Задать вопрос
  • Что пришло на смену кэшу запросов в Mysql?

    ipatiev
    @ipatiev
    Потомок старинного рода Ипатьевых-Колотитьевых
    В Oracle Mysql/Percona теперь кэша запросов нет вообще. Потому что не нужно и вредно.
    Вместо этого, при необходимости, точечно кэшировать отдельные запросы, на клиенте.
    (Очевидные вещи, типа тюнинга конфигурации сервера и оптимизации запросов я здесь не упоминаю, они сами собой разумеются, и к кэшированию прямого отношения не имеют).

    Ну или использовать MariaDB, там кэш пока ещё остался.
    Ответ написан
  • Можно ли использовать return;?

    ipatiev
    @ipatiev Куратор тега PHP
    Потомок старинного рода Ипатьевых-Колотитьевых
    return; - это бессмыслица, её надо убрать из кода
    И никакое false она не возвращает.
    Про "еще одно противоположное значение" вас тоже обманули

    Если функции нечего вернуть, то ничего возвращать она и не должна.

    Максимум, где можно использовать пустой return - если он используется для управления ходои исполнения. То есть чтобы досрочно завершить исполнение кода
    Ответ написан
    Комментировать
  • Как вызвать функцию класса php из onclick?

    ipatiev
    @ipatiev Куратор тега PHP
    Потомок старинного рода Ипатьевых-Колотитьевых
    Никак.
    Функцию РНР "из onclick" вызвать нельзя
    Можно вызвать РНР скрипт только целиком, передав ему данные. обычным аяксом
    А уже в РНР можно написать условие, которое, в зависимости от переданных аяксом данных, создаст экземпляр класса и выполнит тот или иной метод.
    Ответ написан
    Комментировать
  • Is_file, file_exist говорят что файла нет, но он есть?

    ipatiev
    @ipatiev Куратор тега PHP
    Потомок старинного рода Ипатьевых-Колотитьевых
    Если видимые пути полностью совпадают, даже в регистре символов, то дело скорее всего в невидимых символах. Например это может быть перевод строки при чтении из текстового файла.
    Для того чтобы их увидеть, можно набросать функцию типа такой
    function print_nonprintable($string) {
        $i = -1;
        $ret = '';
        while(isset($string[++$i])) {
            $ret .= ctype_print($string[$i]) ? $string[$i] : urlencode($string[$i]);
        }
        return $ret;
    }


    И использовать её в сообщении об ошибке. Тогда проблема сразу станет видна.
    Правда, эта функция изуродует русский текст, но с поддержкой многобайтных символов у меня сходу решения нет
    Ответ написан
    Комментировать
  • Как спроектировать систему подписок на сайте?

    ipatiev
    @ipatiev
    Потомок старинного рода Ипатьевых-Колотитьевых
    одна таблица subscribes с вот такой структурой:

    subscribe_id
    subscribe_author_id
    subscribe_object_id

    и, разумеется, выкинуть счетчики из таблицы users
    больше ничего не нужно
    для остального учить базовый SQL. Все подписки пользователя удаляются одним запросом. Все подписчики - тоже.

    Если оставить в стороне нелепые вопросы "а для запроса на удаление тыщи записей какой-то другой SQL нужен?", и вернуться проектированию подписок, то, как правильно подсказывает Slava Rozhnev,

    Во-первых, в таблицу подписок необходимо добавить два составных индекса,
    subscribe_author_id, subscribe_object_id
    subscribe_object_id, subscribe_author_id
    и тогда ужасный запрос count(*) перестанет быть ночным кошмаром, а будет выполняться мгновенно

    А во-вторых, в неё можно добавить внешние ключи, которые будут ссылаться на таблицу users, с опцией каскадного удаления. Тогда отдельный запрос на удаление подписок и вовсе не придётся писать руками, достаточно будет удалить только юзера.

    Запроса на удаление бояться не надо. Этот запрос всего лишь пометит нужные записи, как удалённые, никто файл на диске укорачивать не будет. Потом база данных использует эти же самые ячейки для других подписок.
    Ответ написан
    1 комментарий
  • Почему число не хочет преобразовываться в строку?

    ipatiev
    @ipatiev Куратор тега PHP
    Потомок старинного рода Ипатьевых-Колотитьевых
    Это интересный вопрос, одна из неочевидностей РНР, впрочем, документированная

    Дополнительно с ключом key будут сделаны следующие преобразования:

    • Строки (string), содержащие целое число (int) (исключая случаи, когда число предваряется знаком +) будут преобразованы к типу int. Например, ключ со значением "8" будет в действительности сохранён со значением 8. С другой стороны, значение "08" не будет преобразовано, так как оно не является корректным десятичным целым.


    В свое время я очень крепко налетел на этом преобразовании. тоже думал, что строки кладу ключами...
    Ответ написан
    2 комментария
  • Как попасть в менеджмент в IT?

    ipatiev
    @ipatiev
    Потомок старинного рода Ипатьевых-Колотитьевых
    Что делать, если очень хочется вайти, но с алгоритмами и структурами данных не получается?
    Так и быть, придётся из эникейщиков сразу в начальники, буду руководить.
    Ответ написан
    6 комментариев
  • ООП в php - не понимаю объекты, неправильно передаю ссылки?

    ipatiev
    @ipatiev Куратор тега PHP
    Потомок старинного рода Ипатьевых-Колотитьевых
    Здесь неправильно не то что всё, а даже больше.
    Потому что ёще до того как вы взялись писать этот "класс", не выучив даже базовый ООП синтаксис, код вашей "функции" уже был очень плохой.

    Я сейчас напишу минимально приемлемый вариант, но повторять его не надо. Потому что всё равно непонятно будет.
    Надо забыть временно про классы и учить базовый синтаксис РНР. Просто потому что сначала надо выучить базовые понятия - работу с БД, обработку ошибок, разделение ответственности:
    - работа с переменными в запросе ведётся через параметризованные запросы
    - код класса не должно тошнить прямо на экран сообщениями об ошибках
    - метод getArray не должен возвращать объект класса mysqli_result. он должен возвращать массив
    - код, который будет в дальнейшем работать с результатом вызова метода getArray, не должен ничего знать про базу данных

    Про сам же код ООП надо хотя бы один раз посмотреть его в учебнике, а не писать на основе чистой фантазии.
    class CProducts
    {
        private $link;
        public function __construct(mysqli $link) {
            $thi->link = $link;
        }
        public function getArray($lim) {
            $query = "SELECT * FROM products ORDER BY DATE_CREATE DESC LIMIT ?";
            $stmt = $this->link->prepare($query);
            $stmt->bind_param("s", $lim);
            $stmt->exeсute();
            $result = $stmt->get_result();
            return $result->fetch_all(MYSQLI_ASSOC);
        }
    }
     
    mysqli_report(MYSQLI_REPORT_ERROR | MYSQLI_REPORT_STRICT);
    $db = new mysqli($host, $user, $pass, $dbname);
    $db->set_charset('utf8mb4');
    $db->options(MYSQLI_OPT_INT_AND_FLOAT_NATIVE, 1);
      
    $product = new CProducts($db);
    $result = $product->getArray(3);
    Ответ написан
    Комментировать
  • Как лучше сделать сохранение в базу данных из нескольких запросов для одинаковых полей в базе данных?

    ipatiev
    @ipatiev
    Потомок старинного рода Ипатьевых-Колотитьевых
    Это какой-то ужас.
    Я не знаю, вопрос звучит как "Мне надо надеть штаны на голову и выйти погулять. Я думаю продеть в штанины руки, зайти в туалет, облиться холодной водой, высохнуть, надеть штаны на голову и идти гулять. Вот только боюсь простудиться, потому что вода холодная".

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

    Надо сделать отдельную таблицу, где будут разные поля, которые привязываются к пользователю по его id. И никаких проблем при редактировании этих полей никогда не будет.

    Я имею в виду что должна это быть одна таблица, которая линкуется к текущей по связи один-ко-многим: таблица из трех колонок - id, user_id и собственно то значение, которое надо менять. Таким образом подмножество этой таблицы с одним и тем же user_id будет представлять из себя то самое "поле", которые вы пытаетесь редактировать сейчас. Но при этом все элементы будут лежать в отдельных строках, и редактироваться обычными SQL запросами.
    Ответ написан
    Комментировать
  • Не поддерживает русский язык, формат xls?

    ipatiev
    @ipatiev Куратор тега PHP
    Потомок старинного рода Ипатьевых-Колотитьевых
    Разумеется, Excel прекрасно поддерживает русский язык. Вот только работает он на старой, как экскремент мамонта, операционной системе Виндоус, где до сих пор стандартной считается кодировка 1251. И думает, что данные всегда лежат в ней.

    Плюс формируете вы не xls, а HTML, замаскированный под xls.
    И из-за этой маскировки Excel не предлагает поменять кодировку при импорте.

    Поэтому есть два пути
    1. Сохранять данные как CSV. Тогда при импорте можно будет выбрать кодировку.
    2. Перекодировать данные перед сохранением,
    mb_convert_encoding($output, "windows-1251", "utf-8");
    Ответ написан
    Комментировать
  • Почему не выводится последний элемент из бд mysql?

    ipatiev
    @ipatiev Куратор тега PHP
    Потомок старинного рода Ипатьевых-Колотитьевых
    Вопрос "почему не выводится" здесь неуместен. Здесь скорее подойдёт вопрос "Этот код вообще хоть как-то работает?" Спойлер: нет.

    Этот код неправильный по стольким параметрам, что у меня просто нет слов.
    Он писался явно без малейшего понимания, а просто методом "подставлю какой-то код, авось подойдёт".
    Причём понимания нет ни на каком уровне - ни того как работает БД, ни того как работает РНР, ни того как РНР работает с БД. Ни даже простого житейского здравого смысла. Зачем в message_get() все эти $user_name = mysqli_real_escape_string ($username);?

    Во-первых, с помощью LAST_INSERT_ID получить "последнюю запись" можно только сразу после вставки. А поскольку в "основном коде" получение сообщения явно не выполняется в одной ветке с записью, то LAST_INSERT_ID не сработает. Причём тут даже простой житейской логики нет. Если сначала один пользователь добавил сообщение, а потом второй, то при получении "последнего" как БД узнает, чьё "последнее" сообщение надо показать?
    Чтобы показать последнее сообщение для определённого пользователя, надо, как правильно отметили в комментариях, надо отсортировать таблицу по времени добавления и выбрать только 1 строку с помощью LIMIT.
    Но кроме этого надо указать, для какого пользователя мы получаем это сообщение.

    Во-вторых, функция mysqli_real_escape_string() вызывается неправильно, она будет выдавать ошибку. А по-хорошему вообще нужно использовать не её, а подготовленные выражения.

    В-третьих, 'message' в запросе вернёт слово 'message', а совсем не само сообщение.

    В-четвёртых, view_message хочет показать несколько значений, но в запросе выбирается только это 'message'

    Во-пятых, как правильно написали выше, функция ни сама ничего не возвращает, ни даже не получает запрошенную из БД информацию. Функция должна выглядеть по крайней мере так

    function message_get($user_id) {
        global $db;
        $chat_id = mysqli_real_escape_string($db,$user_id);
        $query = "SELECT message_id, user_id as chat_id,  message as `text` 
            FROM `secret_messages` 
            WHERE user_id='$chat_id' ORDER BY id DESC LIMIT 1";
        $result = mysqli_query($db, $query);
        return $result->fetch_assoc();
    }

    и потом получать при вызове
    $post = message_get($user_id);
    Ответ написан
    Комментировать
  • Какая нужна теоретическая база на собеседовании джуна?

    ipatiev
    @ipatiev
    Потомок старинного рода Ипатьевых-Колотитьевых
    Реальное понимание ООП и паттернов - это не уровень джуна.
    И да - как вы верно заметили - те кто говорят, на самом деле просто заучили пару расхожих заклинаний.
    Как метко сказано в последней книжке Пелевина,
    Маня была счастлива. Вот что значит быть дочкой банкира - папа не объяснял, папа инструктировал, как объяснять другим".

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

    В реальности от джуна требуется чисто механическая часть ООП:
    - уметь использовать готовые классы, уверенно обращаться к свойствам и методам
    - знать что делают основные магические методы
    - понимать неймспейсы и автолоад
    - в целом уверенно читать исходный код классов - то есть не пугаться слов implements и use (которое трейты а не неймспейсы)
    - уметь использовать контрол-клик в Шторме
    Ответ написан
    3 комментария