Запрос на pg_field_type

Страшно удивился, когда увидел в логах «Постгреса» запрос, которого не было в коде нашего продукта:

select oid,typname from pg_type

Как-то сразу догадался, что он порождается вызовом pg_field_type, который у нас используется, чтобы прозрачно для верхнего уровня обрабатывать тип bytea. Заменил вызов на pg_field_type_oid и запрос пропал.

Проблемы, конечно, особой в этом нет — запрос плёвый, тем более он выполняется только при первом вызове pg_field_type, но как-то неприятно, когда на каждый запуск прилетает полторы тысячи с гаком строк, которые я не заказывал, люблю контролировать такие вещи.

Оставить комментарий

Mosh

Клиент mosh (40.65КиБ)
Окно клиента, когда пропало соединение

Погонял несколько дней в качестве клиента «мош» — «мобильный шелл». Хорошая штука, логинится через эсэсаш, далее поднимает на удалённой стороне свой сервер и открывает свой шифрованный канал через ЮДиПи. Ключи авторизации тоже естественно поддерживаются.

Штука в том, что при разрыве соединения сессия не пропадает, а терпеливо ждёт возобновления — такая помесь эсэсаша и скрина, смены айпи ей тоже не страшны. Другая фишка — если канал пропал или на нём высокие задержки, делаются локальные предсказания поведения курсора, то есть можно печатать и передвигаться по тексту, даже если соединения нет.

Пока всё работает не очень стабильно, но всё равно выглядит как шаг вперёд. У меня время от времени пропадают буквы на выводе самых обычных команд, иногда по экрану скачет курсор или текст выводится не в том месте, но в целом пользовать можно.

Ставится просто — поддерживаются все основные системы, ставите на обе стороны, запускаете из командной строки (mosh имя_сервера вместо ssh имя_сервера) и всё работает.

5 комментариев

Ускорение пользовательских функций в PostgreSQL

Мы ещё в процессе перевода последних наших проектов с «Оракла» на «Постгрес», поэтому всё ещё не закончили избавляться от характерных для диалекта «Оракла» функций, тащим их с собой — пока так проще.

В попытке как-то их ускорить, наткнулся на странность. Возможно это где-то описано, я пока не нашёл это место в руководстве.

Ниже две функции на разных языках, поддерживаемых «Постгресом», по смыслу идентичные — обе представляют собой замену функции NVL2 «Оракла» над целыми числами:

CREATE FUNCTION nvl2_plpgsql(a numeric, b numeric, c numeric) RETURNS numeric AS '
BEGIN
  IF a IS NULL
    THEN RETURN c;
    ELSE RETURN b;
  END IF;
END;
' LANGUAGE plpgsql IMMUTABLE;

CREATE FUNCTION nvl2_sql(a numeric, b numeric, c numeric) RETURNS numeric AS '
SELECT CASE WHEN a IS NULL THEN c ELSE b END;
' LANGUAGE SQL IMMUTABLE;

Будет ли какая-то разница в производительности? Посмотрим на тесты:

 p95=# EXPLAIN ANALYZE SELECT nvl2_plpgsql(g, 0, 0) FROM generate_series(1, 10000000) _(g);

 Planning time: 0.066 ms  Execution time: 38881.927 ms

p95=# EXPLAIN ANALYZE SELECT nvl2_sql(g, 0, 0) FROM generate_series(1, 10000000) _(g);

 Planning time: 0.253 ms  Execution time: 15435.231 ms

Как ни странно, функция на чистом ЭсКуЭле быстрее. Судя по моим экспериментам, так всегда. Иногда результаты различаются вдвое, иногда на порядок — зависит от того, что она делает, но как правило быстрее, обратных примеров я ещё не встречал.

Это неплохое подспорье, так как у нас такие функции встречаются не только в самих запросах, но и в функциональных индексах, значит ускорятся не только чтения, но и вставки.

Оставить комментарий

PostgreSQL и PHP — слон слону не товарищ

Продолжаю серию удивительных открытий в мире перехода на «Постгрес». В документации к функции pg_execute есть малозаметное примечание к последнему параметру — в нём передаются значения для запроса:

Warning Elements are converted to strings by calling this function.

Думаю мало кто обращает на него внимания, собственно, я тоже не обращал. Прежде чем двинуться дальше, разберёмся — что же здесь написано?

Перевод такой: все значения, которые передаются, приводятся к строкам. Код, который это выполняется выглядит так (взял из ПХП 7.2):

if (num_params > 0) {
        int i = 0;
        params = (char **)safe_emalloc(sizeof(char *), num_params, 0);

        ZEND_HASH_FOREACH_VAL(Z_ARRVAL_P(pv_param_arr), tmp) {
                ZVAL_DEREF(tmp);
                if (Z_TYPE_P(tmp) == IS_NULL) {
                        params[i] = NULL;
                } else {
                        zval tmp_val;

                        ZVAL_COPY(&tmp_val, tmp);
                        convert_to_cstring(&tmp_val);
                        params[i] = estrndup(Z_STRVAL(tmp_val), Z_STRLEN(tmp_val));
                        zval_ptr_dtor(&tmp_val);
                }
                i++;
        } ZEND_HASH_FOREACH_END();
}

pgsql_result = PQexecParams(pgsql, query, num_params,
                                NULL, (const char * const *)params, NULL, NULL, 0);

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

Думаю, это связано с типизацией «Постгреса». Взять к примеру числа — два числовых типа ПХП нельзя адекватно преобразовать в россыпь типов «Постгреса», а если привести к неверному типу будут проблемы — в этой СУБД есть понятие перерузки функций, то есть функция выбирается не только по имени, но и по числу и типам параметров.

Поэтому и выбраны строки — они приведутся к нужному числовому типу сами собой, со строками это работает. К сожалению в этом преобразовании кроются и проблемы.

Ещё когда мы работали только с «Ораклом», заметили, что если вместо чисел привязывать строки, то иногда планы выполнения запросов меняются в худшую сторону. Лёгкость обращения с типами в ПХП иногда к этому приводит — переменная, используемая для хранения числа, имеет строковый тип.

К счастью, в оракловом модуле это легко решается — при привязке надо всего лишь указать, что тут мы имеем ввиду число, сами собой совершатся нужные преобразования и «Оракл» так устроен, что никаких проблем это не породит.

В «Постгресе» проблемы будут, я их описал выше, так ещё и способа хорошего нет — все функции любого модуля для работы с этой базой, доступные в ПХП любой версии, преобразуют все числа в строки. К несчастью, в «Постгресе» проблема изменения планов тоже имеет место — недавно наткнулись на запрос, который через ПХП выполняется почти полторы секунды, а через консольный клиент — меньше миллисекунды.

Мой братишка придумал оригинальное решение — определять позиции на которых мы привязываем числа и автоматически внутри нашего фреймворка в этом месте запроса указывать тип bigint явным образом. То есть добавлять после плейсхолдера параметра конструкцию «::bigint».

Пришлось изменить несколько наших хранимых процедур, но в целом всё плошло довольно гладко.

1 комментарий

Снова о Стрелковых и Шапкиных

Запись в метрической книге: 11 ноября 1879 года крещены крестьяне деревни Коптевой Варвара Васильева и Ларина, православного вероисповедания, первый брак.
Выписка о бракосочетании из метрической книги деревни Новое Исаково

Я как-то упоминал три года назад, что у меня есть предок, который, как мне кажется, не разобрался в концепции фамилий в своё время. Он сам и часть его детей какое-то время записывались под фамилией жены — Шапкины, а позже он получил собственную фамилию — Стрелков.

На скриншоте выше выписка за 1907 год, где косвенно упомянута смена парадигмы — мой двоюродный прадедушка Василий Павлович записан сразу под двумя фамилиями.

2 комментария

Огород над печью для обжига

Глазурь на кирпиче (63.08КиБ)
Глазурь на кирпиче, вынутого из стены старинной промышленной печи

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

На днях посещал музей дома культуры железнодорожников в посёлке Юдино близ Казани, хранительница музея случайно узнала об этом моём хобби и показала кирпич, который на фото выше.

Она живёт в частном доме, в посёлке Красная Горка. Её муж и сын, копая яму под какие-то хозяйственные нужды, докопали до слоя кирпичей, выкорчевали несколько и поняли, что наткнулись на печь для обжига. Связались с историками из Казани, те приезжали к ним и в частности рассказали, что это третья такая находка, то есть такие печи находят, но это редкость.

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

Оставить комментарий

Дореволюционный «Однер»

Арифмометр Однера (73.83КиБ)
Арифмометр Однера 1906 года, выпущенный фабрикой в Санкт-Петербурге

Из-под Астрахани в наш музей приехал дореволюционный арифмометр Однера 1906 года. К сожалению, на нём год уже не написан — он был на шильдике, который пропал вместе со сгнившим деревянным основанием, но дореволюционная орфограция видна невооружённым взглядом.

О Вильгодте Теофиле Однере я уже рассказывал — это шведско-русский механик, который в 1868 году приехал в Питер, где остался до конца своей жизни. В он 1877 выпустил первый арифмометр собственной конструкции, который стал невероятно коммерчески успешным.

В 1905 году Вильгодт умер и управление компанией перешло к его сыну и партнёру отца — Френку Хиллу. После революции компанию национализировали, бывшие владельцы переехали в Швецию, в СССР же знаменитые арифмометры выпускались ещё очень долго. Знаменитые «Феликсы» — это, по сути, клон «Однера» с модификациями.

Благодаря моей бабушке, которая забрала с предприятия списанный «Феликс», я с детства умею обращаться с такими машинками, но этот экземпляр уже не рабочий — сильно заржавел, зато обошёлся дешевле рабочих моделей.

Оставить комментарий

Матфей и Стефан

Схема родословной семьи Стрелковых: Тимофей Стрелков → Матфей и Федосья Стрелковы → Стефан (1837–?), Егор и Роман Стрелковы.
Мои загадочные предки — Матфей Тимофеевич и Стефан Матфеевич

А вот, например, странная вещь, которая не даёт мне покоя. Есть у меня такая ветка — Стрелковы/Шапкины, я о них писал буквально недавно.

Стефан на рисунке выше — мой прямой предок, прапрапрадед, родился по Бугульмой, в деревне Старое Чирково. Странность в том, что его зовут именно Стефан, а отца — Матфей, оба через «ф», хотя рядом навалом Матвеев и Степанов — записи об их крещении на соседних страницах.

С одной стороны, спасибо — так гораздо проще устанавливать родство. С другой стороны — откуда такое различие? Как версия — возможно мои предки с этой стороны не русские, а например обрусевшие поляки.

Продолжая версию — там Солдатская Письмянка недалеко, одна её сторона называлась в те времена «Панской», может они оттуда? Фамилия «Стрелковы» может указывать на военное происхождение.

8 комментариев

← сюда туда →