Ответы пользователя по тегу PHP
  • Почему функция обработки ошибок по какому-то "соглашению программистов" должна первым параметром принимать/возвращать код ошибки, а не сообщение?

    gzhegow
    @gzhegow Автор вопроса
    aka "ОбнимиБизнесмена"
    Судя по числу подписавшихся одно хочу точно сказать, если на форуме влупить фразу "по соглашению программистов" верит чрезвычайно больше народу, чем если влупить "я тут подумал, почему бы не сделать..." - видимо так и работает
    Ответ написан
    1 комментарий
  • Как быстро сравнить большое число прайс-листов с данными в БД?

    gzhegow
    @gzhegow
    aka "ОбнимиБизнесмена"
    Скрипт у меня где-то был который сравнивает удаленный массив с локальной копией и возвращает дельту изменений (массивы для прямой загрузки в бд) без потерь старых данных.

    Ща я тебе скрипт скину погодь
    // получаем локальное хранилище (тут может быть запрос в БД)
    // * функция _pluck работает примерно как array_column только умнее - обрезает массив именованных массивов оставляя в каждом ключе значение только одной ячейки вместо всего массива, в underscore/lodash такая штука есть), вторым параметром принимает массив нужных полей (в нашем случае - null = весь массив без изменений), в третьем - колонку, которая станет ключом - то есть здесь получилось чтобы просто значения колонки code, сделали ключами
    $full_arr = _pluck(json_decode(file_get_contents($this->full_path), true), null, "code");
    
    // получаем удаленное хранилище (тут запрос на другой сервер, потом переназначение колонок, проверка минимального их количества, проверка значений данных)
    $current_arr = $this->getData();
    
    
    // получаем УДАЛЕННЫЕ товары
    // - в товаре не хватает полей
    // - товар с таким кодом когда-то был, а теперь исчез
    // - количество товара меньше требуемого
    
    // для этого
    // 1. получить плохие элементы из текущей выгрузки
    // 2. получить элементы, которые раньше когда-либо попадались, а теперь их почему-то нету
    // 3. получить элементы, в которых количество меньше требуемого
    // 4. проставить им флаг "удаленный"
    // 5. в массив для синхронизации добавить только те удаленные, которые не были удалены раньше
    $process_current_arr = array_filter($current_arr, function ($v) {
    
      // тут функция проверяющая наличие колонок для сравнения - ну то есть сравнение производится по такому-то набору колонок id, code, param1, param2, нужно убедится что эти колонки есть, в противном случае элемент ставится как плохой
      return $this->filterData($v);
    
    });
    $deleted_arr = array_diff_key($current_arr, $process_current_arr);
    $deleted_arr = array_replace($deleted_arr, array_diff_key($full_arr, $process_current_arr));
    $deleted_arr = array_replace($deleted_arr, array_filter($process_current_arr, function ($v) {
      return ($v["count"] < $this->count);
    }));
    $deleted_arr = array_map(function ($v) {
      $v["deleted"] = 1;
      return $v;
    }, $deleted_arr);
    $process_current_arr = array_diff_key($process_current_arr, $deleted_arr);
    $sync_arr = array_replace($sync_arr, array_intersect_key($deleted_arr, array_filter(array_replace($deleted_arr, array_intersect_key($full_arr, $deleted_arr)), function ($v) {
      return (empty($v["deleted"]));
    })));
    
    
    // получаем ВОССТАНОВЛЕННЫЕ товары
    // - товары которые были удалены, а теперь они соответствуют требованиям
    
    // для этого
    // 1. находим удаленные товары в нашем хранилище
    // 2. методом исключения определяем, какие товары есть в нашей выгрузке
    $recovered_arr = array_intersect_key($process_current_arr, array_filter($full_arr, function ($v) {
      return (!empty($v["deleted"]) && (strval($v["deleted"]) === "1"));
    }));
    $recovered_arr = array_map(function ($v) {
      $v["deleted"] = 0;
      return $v;
    }, $recovered_arr);
    $sync_arr = array_replace($sync_arr, $recovered_arr);
    $process_current_arr = array_diff_key($process_current_arr, $recovered_arr);
    
    
    // получаем НОВЫЕ товары
    // - товары которых в нашем хранилище нету
    
    // для этого
    // 1. методом исключения по коду сравниваем хранилище и оставшиеся для обработки элементы
    $new_arr = array_diff_key($process_current_arr, $full_arr);
    $sync_arr = array_replace($sync_arr, $new_arr);
    $process_current_arr = array_diff_key($process_current_arr, $new_arr);
    
    
    // получаем ИЗМЕНЕННЫЕ товары
    // - товары которые есть и в нашем хранилище и в выгрузке, но данные отличаются
    
    // для этого
    // 1. методом соответствия по хешу сравниваем хранилище и оставшиеся для обработки элементы
    // * hashData - функция которая отбирает из массива значения нужных колонок и по ним делает хеш, не учитывая остальное
    $process_current_arr_md5 = array_combine(array_map(array($this, "hashData"), $process_current_arr), $process_current_arr);
    $full_arr_md5 = array_combine(array_map(array($this, "hashData"), $full_arr), $full_arr);
    $updated_arr = _pluck(array_diff_key($process_current_arr_md5, $full_arr_md5), null, "code");
    $sync_arr = array_replace($sync_arr, $updated_arr);
    $process_current_arr = array_diff_key($process_current_arr, $updated_arr);
    
    
    // Соединяем старые данные с новыми, чтобы ничего не потерять
    $filemtime = date("Y-m-d H:i:s", filemtime($this->sync_path));
    $sync_arr = array_replace(array_intersect_key($full_arr, $sync_arr), $sync_arr);
    
    
    // Тут в конце соединяем наш full и sync, сохраняем или просто sync выводим, чтобы увидеть отличающиеся записи в прайсе и бд


    Попробуй потестить может какие глюки найдешь, то я тоже исправлю
    Ответ написан
    Комментировать
  • Что такое Шаблон и Вид в MVC и разница между ними?

    gzhegow
    @gzhegow
    aka "ОбнимиБизнесмена"
    Ну у меня так получалось - Вид выгледел как класс, а шаблон как html. Формально вид получал данные из контроллера, чтобы потом выбрать шаблон-обертку со скриптами, и выдать результат, но это может и не совсем верно, если учесть что верно вообще хрен знает как.

    Ну то есть "правильно" с точки зрения подхода - это в каждом контроллере подключать все файлы скриптов от вашей верстки (чтобы потом их сжать например) - но если у вас 100 контроллеров, то что - 100 раз подключать?

    Получается надо другому контроллеру это сбагрить, а если он тоже контроллер, то получается его если хотеть можно вызвать через роут. А как ты вызовешь через роут внешний вид без контента - лишено смысла. Вот некоторые и отделяют этакий "контроллер" подгружающий скрипты, называя его Вид и делая его классом. Правильно или нет - не знаю, позволяет написать вариант отображения один раз и хранить его отдельно от остального кода, который работает с данными, сэкономить время.

    Вон в яваскрипте response.send(text) верно из контроллера, тут мы почему-то решили что все должно темплейтом заканчиваться

    Такто веб работает запрос-ответ. Шаблон MVC позволяет вам немножко:
    - разделить файлы по папкам в первую очередь в своем мозгу
    - избавится от бесконечных require dirname(__FILE__) . "/path/to/damn/foo/bar/file.php" заменив их более удобным $this->load->template("file")
    - но потом снова ударится в то, что данные нужно передавать туда сюда и в конце все равно прийти к тому, что основной файл (контроллер?) должен выдавать ответ и выставлять код ответа...

    Прикол то в чем, ответ сайта предполагает обработку ошибок и выбор контента, который ты отдашь. Так например если в HTTP_ACCEPT лежит "application/json", то ваш контроллер вообще не должен подгружать никакие виды (он будет "echo $content;" который на самом деле не $content, а вполне стандартный массив вида (status, errorcode, message, data); таким образом понятие вида которое то есть то нет не может быть стандартом его наличия.

    Вот например, вам нужно вывести ошибку о том, что файла вида для ошибки нету. Что делать? Проверить наличие файла и вывести вид, которого нет? Фигня. Ответом управляет отдельный класс/файл/модуль/компонент, в который вы просто передадите шаблон, опять же при вызове определенных контроллеров, а контроллер был вызван роутером разбором исходного адреса.

    Отсюда можно сказать, что сам шаблон MVC реализуется всего одним модулем - Loader, который имеет spl_autoload_register() и $obj = new $class() (для моделей Model::getInstance()); $obj->init(); return $obj; В случае ошибки класс Loader вызывает собственный метод error(), который передает управление классу Request, а поскольку существует некое такое обязательство полной несвязности классов напрямую, чтобы они могли отдельно функционировать, то простите как? Loader->error() не может вызывать Request->send() потому что это отдельные модули. Значит нужен общий модуль, именуемый ядро, который и решает, что если модуль подключен, то он выдает ответ, иначе print_r();die(); - там нормальное такое путало...

    Некоторые потом начинают играть в "события". Ну как же дескать - если прямой связанности быть не может, чтобы модули были отдельные друг от друга, то надо получается, чтобы происходил обмен приказами, которые просто громко звучат на все приложение и начинают сюда систему событий прикручивать, делая из php -> js, чтобы было удобнее соответствовать "правильному стандарту", которого нет.

    Это просто про то, что файлы лежат в определенных папках, и их можно подключать постоянно не просчитывая пути до них.
    Ответ написан
    Комментировать
  • Как реализовать сайт расписания занятий?

    gzhegow
    @gzhegow
    aka "ОбнимиБизнесмена"
    Непростая, но реализуемая.

    Я бы хранил смещение от начала дня чтобы задать время отправления/прибытия в конкретный день

    Храните где угодно - это не принципиально, ваш код модели должен уметь получить данные из того файла где ВАМ удобнее хранить
    БД реляционная результаты выдаст быстрее и для диплома здесь бы хватило с крышей
    Захотите вывести в таблицу ворда или чего еще - это уже чуть другая задача
    Считывать из ворда / экселя - бред - долго читать, долго комбинировать, долго искать, а еще надо будет кешировать, оптимизировать - нафиг надо.

    Для диплома запользуйте реляционную БД которую знаете.

    Вы храните маршруты с временем прибытия/отправления, временем в пути, временем стоянки и все что необходимо в таблице "маршруты".

    К маршрутам привязываются станции, где будут остановки.

    Если человек хочет уехать сегодня - он выбрал метку времени, выбрал свою станцию, выбрал куда хочет попасть.

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

    Задача не из простых, но когда сделаете сможете чуть ли не торговые маршруты считать, задача продается людям которые часто сигают через границу в соседнюю страну за покупками, задача продается игроманам космических игр, задача продается компаниям типа яндекса, но они не купят, у них своих головастиков с крышей.
    Ответ написан
    9 комментариев
  • Как в PHP отправить файл, который в строке?

    gzhegow
    @gzhegow
    aka "ОбнимиБизнесмена"
    ну куда-то он точно сохранится, ваш файл.
    можно конечно долго долго курить ман и чуть ли не телом запроса этот файл отправить.
    Но как по мне, то строка ваша все равно в переменной, а переменную можно передать в ответ, поставив заголовок файла в ваш запрос (можно гуглить по фразе форсировать-закачку-файла)
    Ответ написан
    Комментировать
  • Почему при редактировании шаблона html слетают теги?

    gzhegow
    @gzhegow
    aka "ОбнимиБизнесмена"
    У битрикса стоит защита, там есть модуль родной заводской кажется "сканер безопасности".
    Проще говоря на вашего пользователя нет прав размещать теги <script> в коде.
    Нужно попросить админа изменить права для вашего юзера.
    Ответ написан
    Комментировать
  • Почему код сортировки работает не так как ожидается?

    gzhegow
    @gzhegow Автор вопроса
    aka "ОбнимиБизнесмена"
    ОБНОВЛЕНО 06.12.2016
    sandbox.onlinephpfunctions.com/code/41ea9f04b0e9b2...

    Внимание, функция tree() используется для вывода. В нашем случае мы получили массив, в случае вложенного меню, в ней нужно работать прямо с версткой, поскольку результирующий массив можно будет вывести в виде дерева на плоскости, с выводом одно-внутри-другого будут проблемы, поскольку это все одна коллекция.

    <?php
    error_reporting(0);
    
    // эмуляция БД - если у вас SQL - это не нужно
    $menu = array(
        array("id", "parent_id", "level"),
        
        array(1, 0, 0),
        array(2, 0, 0),
        array(3, 0, 0),
        array(4, 0, 0),
        array(5, 0, 0),
        array(6, 0, 0),
        array(7, 0, 0),
        array(8, 0, 0),
        array(9, 0, 0),
        array(10, 0, 0),
        array(11, 0, 0),
        
        array(17, 15, 1),
        array(18, 15, 1),
        array(19, 15, 1),
        array(20, 15, 1),
        array(21, 15, 1),
        array(22, 15, 1),
        array(23, 15, 1),
        array(17, 1, 2),
        array(18, 1, 2),
        array(19, 1, 2),
        array(20, 1, 2),
        array(21, 1, 2),
        array(22, 1, 2),
        array(23, 1, 2),
        
        array(24, 16, 1),
        array(25, 16, 1),
        array(26, 16, 1),
        array(27, 16, 1),
        array(28, 16, 1),
        array(24, 2, 2),
        array(25, 2, 2),
        array(26, 2, 2),
        array(27, 2, 2),
        array(28, 2, 2),    
    
        array(12, 1, 1),
        array(13, 1, 1),
        array(14, 1, 1),
        array(15, 1, 1),
        
        array(16, 2, 1),
    );
    $columns = array_shift($menu);
    $menu = array_map(function ($v) use ($columns) {
        return array_combine($columns, array_replace(array_fill(0, count($columns), NULL), $v));
    }, $menu);
    
    
    // сортируем правильно - если у вас SQL - делайте в запросе
    usort($menu, function ($a, $b) {
       return 0
        ?: ($a["level"] - $b["level"])
        ?: ($a["parent_id"] - $b["parent_id"])
        ?: ($a["id"] - $b["id"]);
    });
    
    
    // выбираем в массив по родителям
    $menu_parents = array();
    foreach ($menu as $v):
        $menu_parents[$v["parent_id"]][] = $v;
    endforeach;
    
    
    // пробегаем каждый элемент собирая потомки по очереди
    function tree($arr, $parent_id = 0, &$res = array()) {
        foreach ($arr[$parent_id] as $v):
            $id = $v["id"];
            if (!isset($res[$id])):
                $res[$id] = $v;
            elseif ($res[$id]["level"] < $v["level"]):
                $res[$id] = $v;
            endif;
            if (isset($arr[$id])):
                tree($arr, $id, $res);
            endif;
        endforeach;
      return $res;
    }
    $menu = tree($menu_parents);
    
    
    echo "<pre>";
    print_r($menu);
    Ответ написан
    Комментировать
  • Почему PCRE (PHP) не читает символ < (меньше) при разборе верстки?

    gzhegow
    @gzhegow Автор вопроса
    aka "ОбнимиБизнесмена"
    Текущее решение:
    <?
      $text = <<<TEXT
        <scriptsrc=""></script>
        <script blablabla src=""></script>
        <script src=""></script>
        <script blabl abla src="123.js"></script>
        <script bla 22bl2 abla src="tanks/tank.js"></script>
    TEXT;
    
      $match = array();
      $tmp = str_replace("<script", "|script", $text);
      preg_match_all('/\|script[^<>]+src=[\'"]([^\'"]+)/ium', $tmp, $match);
    
      echo "<pre>";
      print_r($match);


    Но вопрос все еще актуален! ПОЧЕМУ (мать такая)?
    Ответ написан
    Комментировать
  • Почему запрос из PHP идет 10 секунд, а из консоли или навиката тот же запрос - 0.2 сек?

    gzhegow
    @gzhegow Автор вопроса
    aka "ОбнимиБизнесмена"
    Прошу прощения посетившим, решение найдено, но оно никак не было связано с запросом.
    Проблема была в пользовательской сортировке usort($arr, function () { return mb_strcasecmp($a,$b); }); - слишком долго происходила
    Ответ написан
    Комментировать
  • Как использовать кириллицу в плейсхолдере?

    gzhegow
    @gzhegow
    aka "ОбнимиБизнесмена"
    Давно это было, но есть риск что тебе придется переписывать tvFilters.
    Это называется - попытка разрабов Модикс написать собственный язык программирования, и заставить пользователя его выучить, для того, чтобы не учить язык программирования.
    Попробуй воткнуть в сами ТвФильтры, в код Модикс. Там где-то есть регулярка скорее всего и возможно ты сможешь ее найти. Добро пожаловать к программистам.
    Ответ написан
    Комментировать
  • Как присвоить значение $_SESSION по нажатию на DIV?

    gzhegow
    @gzhegow
    aka "ОбнимиБизнесмена"
    index.html
    <div class="mydiv">
    </div>
    <script src="//code.jquery.com/jquery-1.12.0.min.js"></script>
    <script>
    $.noConflict();
    (function ($) {
      $(function () {
        $('.mydiv').on('click', function() {
          $.ajax('set.php', {
            'clicked_div' : 1
          });
        });
      });
    })(jQuery);
    </script>


    set.php
    <?php
      !empty($_REQUEST['clicked_div']) || exit('Див не нажат');
      $_SESSION['your_data'] = 1;
    Ответ написан
    Комментировать
  • Каков best practice загрузки сторонних файлов в функции?

    gzhegow
    @gzhegow
    aka "ОбнимиБизнесмена"
    а я только что сделал иначе:
    $arr = json_decode(file_get_contents());
    $app = Framework::init();
    $app->config = array_merge($app->config, $arr);

    и так далее хоть 500 конфигов соединить в один.
    Правда там есть косяк, придется array_merge переписать для работы с числовыми ключами
    Могу скинуть код если понравится метод.
    Ответ написан
    Комментировать
  • Должны ли конструкторы подклассов быть приватными при реализации синглтона?

    gzhegow
    @gzhegow
    aka "ОбнимиБизнесмена"
    Кажется я понял что ты имеешь в виду. Сейчас сам как раз копаюсь над этим.
    Ты хочешь микро-модули сделать, которые контроллируются из единой оболочки/шины/модуля, так?

    В JS это очень четко делалось:
    App = {};
    Module = {
      b : function() {}
    };
    App.b = Module.b;
    App.b();

    И все было шоколадно и легко. Почему собственно и делают приложения на Ноде, ибо удобно и не надо страдать гемороем с ПХП.

    В нашем случае эти 4 строчки увеличиваются в код диких размеров. Вкури мой последний вопрос, я как раз сейчас эт сделать пытаюсь. Может чего и выйдет совместными усилиями.
    Ответ написан
  • Как передать верстку через JSON в Javascipt из PHP?

    gzhegow
    @gzhegow Автор вопроса
    aka "ОбнимиБизнесмена"
    php:
    $base64json = base64_encode(json_encode($php_array));


    template:
    <script>
      JSON.parse(atob('<?=$base64json;?>'));
    </script>
    Ответ написан
    1 комментарий
  • Какие возможности WordPress и что выбрать в итоге?

    gzhegow
    @gzhegow
    aka "ОбнимиБизнесмена"
    На вордпрессе тебе хватит 10-ки выверенных плагинов, чтобы сделать хороший блог. Купил тему, поставил плагины, пользуешься.
    Программирование вообще дело не благодарное - потратишь кучу лет, изучишь его и будешь потом днями им заниматься и думать - как было хорошо, когда я занимался бизнесом. Теперь - программист...
    Ответ написан
    Комментировать
  • Комментарии для WordPress, какие есть бесплатные плагины?

    gzhegow
    @gzhegow
    aka "ОбнимиБизнесмена"
    Ой, Вась, ну не жмоть, поставь себе Cackle за 200 рублей в долбанный месяц и избавься от гемора.
    почти 20 социалок, неограниченная вложенность, аякс подгрузка, индексация звездочек в гугле и оценки комментов, и все это за 200 рублей в месяц. Полная модерация, полностью рабочая админка и поддержка с круглосуточным онлайном. Ну на кой черт тебе бесплатное при такой радости, м?
    Ответ написан
    Комментировать
  • В PHP можно ли создать свой формат для файлов (например файл с расширением ".lang")?

    gzhegow
    @gzhegow
    aka "ОбнимиБизнесмена"
    Можно.
    Но сразу говорю, забей, сделай JSON и языки свои делай в этом формате - проще будет подружить разные системы разработки и языки программирования.
    Теперь можешь не поверить, и пойти сломать себе пару мозгов, и все равно к этому прийти.
    Ответ написан
    1 комментарий
  • Какой php фреймворк наиболее прост в освоении?

    gzhegow
    @gzhegow
    aka "ОбнимиБизнесмена"
    А мне нравится Codeigniter и Yii (самое интересное - первый). Я все никак не подружусь с этими вашими phar'ами, и composer'ами, пока не пойму досконально что там происходит, кроме собственно скачивания модулей с одного сервака в режиме терминала.

    На Yii я привык работать с базой данных - даже первый ЭктивРекорд оч простой и работа с языками очень простая (я себе дописал, чтобы генератор кода создавал базу моделей, а мои собственные модели не перезаписывал)

    А кодеигнайтер в принципе фреймворк только от буквы Ф, там есть роутинг, базы данных и действия, все остальное - полная свобода, пустое поле.

    Но все таки как и в каждом фрейворке - странное ощущение что у каждого программиста в башке дыра. И какой ф-ворк не возьми, все равно где-то да дырка, что-то - да не сделано.

    И вроде логично - напиши свой, и, ты думаешь он будет для всех? Нет, ты просто создаешь еще один 101-ый фреймворк.
    Ответ написан
    Комментировать
  • Как реализуется логика дополняющих товаров в интернет-магазине?

    gzhegow
    @gzhegow
    aka "ОбнимиБизнесмена"
    Есть таблица параметров. Есть таблица товаров. Есть таблица товаро-параметров. У текущего товара есть параметры.
    Понятие связанное оно как бы говорит "такие же или плюс минус один", и уже вот эта фраза зашивается в твою страницу на программном коде - что означает плюс минус 1.

    По итогу формируется запрос, который возвращает ID-шки элементов.
    Потом по id-шкам запрашиваются сами элементы.
    Фсо.

    Звони мне в скайп или на емейл пиши, объясню наглядно.
    Ответ написан
    2 комментария
  • Функция json_decode переформатирует числа?

    gzhegow
    @gzhegow
    aka "ОбнимиБизнесмена"
    сначала преобразуй число в строку
    потом регуляркой замени запятые на точки
    а потом уже кодь в json

    Любишь делать проверки?
    Проверь равняется ли исходное число через === тому что получилось. Если нет, запятые заменились. Если да - запятой или не было, или не заменилась.
    Ответ написан
    Комментировать