Информация
- В рейтинге
- Не участвует
- Откуда
- Москва, Москва и Московская обл., Россия
- Дата рождения
- Зарегистрирован
- Активность
Специализация
Архитектор программного обеспечения, Деливери-менеджер
Ведущий
C#
.NET Core
Entity framework
ASP.NET
Базы данных
Высоконагруженные системы
Проектирование архитектуры приложений
Git
PostgreSQL
Docker
Аллокации не коде методов Merge, а в самих асинхронных итераторах.
Звучит как попытка угадать будущее, которая в общем провальна
Потому что архитектура не очень видимо
У нас недавно всплыла проблема, но как на днях выяснили что разработчик накосячил.
Нет ли у вас проблем с проверкой открепленной подписи по ГОСТу с помощью Bouncy Castle?
Спасибо огромное за вашу статью
Внезапно я недавно сделал код, который достает закрытый ключ из сертификата такого формата. Если кому-то будет интересно могу написать статью.
Можно ссылочку на стандарт?
Если у вас не напрямую из базы читали в dwh, а вы сначала из твоей системы отдавали по api данные в другую, а уже оттуда данные попадали в dwh, то тут могла бы помочь интеграция с этой системой на уровне данных. Тем более, судя по всему, там etl типа airflow
То есть целевая модель такая:
Вы выставляете в базе вьюху, которая отдает нужные данные одной таблицей
Обкладываете её индексами
Другая система подключается к вашей с правами только на чтение этой вьюхи
PROFIT!
Вы экономите огромное количество ресурсов на сериализацию данных
Но вы писали что другую систему изменить нельзя (единственный специалист по airflow занят на другой задаче), то просто поменяйте структуру у себя
То есть в вашу базу напрямую не ходили внешние приложение? Тогда почему вы не могли структуру вашей базы поменять?
Про покрывающие индексы стоит говорить если вы запросы в программе сделали с нудными полями. А у вас include, который все равно в select все потащит.
Покрывающий индекс при чтении выгоден всегда. Потому что обычны идекс скан - это поиск записи в индексе (одно логическое чтение), а потом получение записи из кучи (второе логическое чтение). Если вы сделаете «широкий индекс» при выборке относительно небольшого количества строк, то index only наверное всегда выиграет у index scan. Но вы получите большой импакт при записи, так как индексы надо будет обновлять и перестраивать.
Поэтому как общий подход делать все через index only я не могу рекомендовать, но для особо экстремальных случаев помогает даже покрывающий индекс , в котором все поля кроме одного включены.
Про работу над ошибками:
В базах данных есть view, их как раз и нужно использовать при интеграции с другими системами на уровне данных. Причем Вы могли прямо в текущей базе сделать нормальную модель и отдать потребителям view.
Это у вас НЕДОСТАТОЧНАЯ нормализация данных, как и в таблице коммуникантов. Недостаточная нормализация как раз увеличивает объемы, ухудшает возможности оптимизации с помощью индексов и приводит к конфликтам рассогласованности данных.
Вы неверно употребляете термин «нормалмзация». Нормализация это отсутствие связей между не ключевыми полями в таблице и строгая связь с ключевым полем. У вас это просто ошибка моделирования.
Есть хороший инженерный коэффициент - 6. Или более наукообразно - 2Пи. Система должна выдерживать шестикратное превшение нагрузки над «рабочими» значениями. То есть во время тесты вы должны были в 6 раз увеличить объемы данных для тестирования, если у вас проблема упирается именно в объем или rps, если система упирается в частоту запросов.
Выглядит как «из пушки по воробьям».
1) почему вы продолжали использовать include, а не вписали проекции только тех значений что нужны конкретно для dwh? Вряд ли там все поля таблицы используются
2) как следствие пункта выше: почему не пытались сделать покрывающие индексы и свести все к index only scan?
3) почему не применили filtered indexes, вы бы могли для целей dwh сделать индекс c where, чтобы из индекса убирать автоответчики ?
Кроме того можно было сделать в индексе where по дате, чтобы отсекать данные старше 90 дней и перестраивать индекс по ночам, причем конкурентно, чтобы не мешать другим. Получился бы всего один ddl запрос
4) возможно стоило попробовать перенести op_data в jsonb поле в самой activity, тогда и читать пришлось бы меньше (вероятно) и размер возвращемого датасета снизился бы (точно). Делать key-value хранилище в таблицах бд - не самое эффективное решение. В крайнем случае сделать json_agg (два array_agg на key и value)в запросе.
что из написанного вам непонятно? С чем из написанного вы не согласны?
Да, не точно написал. Vacuum не блокирует, но сильно замедляет запросы, так как читает и записывает множество страниц таблицы.
Разве не так сейчас вебсокеты работают https://datatracker.ietf.org/doc/html/rfc8441
Это если http2, но сейчас вроде все серверы и клиенты это поддерживают.
Сделал тест такого варианта https://habr.com/ru/articles/963120/
Очень сильно проигрывает транзакциям в БД, даже без реализации отката при потере связи.
Рукопашные транзакции могут оказаться быстрее если время обработки значительное, но мы тогда приходим к архитектуре с очередями в базе и асинхронной обработке.
Сохранить синхронность и сделать рукопашные транзакции, чтобы уменьшить ожидания на блокировках, в большинстве случаев приведет к замедлению. А если нужно просто уменьшить степень конкурентности, то проще блокировку сделать advisory lock, взять блокировку таблицы или очередь как в этом посте.
Сделал тест варианта с явными блокировками https://habr.com/ru/articles/963120/
В принципе любюй протокол палится своими заголовками. Даже VLESS, судя по описанию легко поддается определению. А не палится он за счет того, что маскируется под http2 с веб-сокетами. Даже не маскируется, он просто свою полезную нагрузку передает через h2+ws. Странно что об этом не сразу догадались.
Насколько я понимаю TLS пока еще никто читать не научился, потому что если научится, то это конец всей безопасности в вебе. Поэтому определить что внутри h2+ws траффика идет VPN туннель пока не могут.
А вот заблокировать ваш сайт и выписать штраф за рекламу ВПН для обхода блокировок - вполне. Странно что администрация хабра спит.
Что именно улучшить? Скорость работы? Надежность? Время написания?
Можете пример кода привести, который демонстрирует эти улучшения?
Я пока увидел, что для реализации цикла с транзакциями внутри, а не снаружи нужен фоновый процесс, который будет отменять незавершенные брони. Тогда как в моем примере из статьи такой процесс не нужен.
Это вообще ни о чем не говорит.
Если для вас ACID и гарантии СУБД это "догмы" и "ярлыки", тогда вы правы. Я вообще не считаю себя умнее разработчиков Postgres\SqlServer\MySQL и даже SQLite, чтобы думать что могу сделать ACID лучше, чем они за любое разумное время.
Code talks. Просто покажите пример.
Да, у меня статья о том как эта проблема решается, если вы не заметили
В этой статье пример кода как раз сталкивается с большим количеством блокировок из-за больших транзакций.
Конечно надежность, которая заключается как раз в соблюдении ACID на уровне запросов пользователей\клиентов сервиса.
Если используете транзакции, то не может быть.
Транзакция будет отменена, резерв не пройдет.
Закоммиченная транзакция никуда не денется, незакоммиченная будет отмена. Это гарантия долговечности - D в ACID
Это я и имею ввиду, когда говорю что "самопальные транзакции" гораздо более затратны. Кроме того у вас нет никакой защиты от Durty Reads.
Пример в статье показывает как обойтись без такой обработки.
Вы вообще статью прочитали? Код смотрели?
При том что вы пытаетесь его реализовать
Если вы не показываете клиенту промежуточный статус, то это тот же самый уровень. По сути вы хотите дать приложению такие же гарантии как от транзакций, но без транзакций. Увы самодельная атомарность и консистентность это очень сложно. А независимость самопальных транзакций почти недостижима при нескольких экземплярах вашего приложения.
Отсутствие атомарности:
Предположим вы реализовали такой цикл с транзакциями внутри цикла. Внезапно на одной из итераций происходит падение БД (внезапная перезагрузка, oom-kill итд). Что будет делать ваш код? Клиент получит свою ошибку, но вам надо как-то откатить уже закомиченные транзакции. А если приложение падает в середине цикла, клиент получает отказ, а кто откатывать будет?
Отсутствие согласованности:
Кроме того можно рассмотреть сценарий параллельных резервирований:
Клиент А зарезервировал товар 1 (транзакция закоммичена)
Клиент Б зарезервировал товар 2 (транзакция закоммичена)
Клиент А пытается резервировать товар 2, но запасы кончились, резрв товара 1 нужно откатить
Отсутствие независимости:
Кроме того ваше приложение скорее всего постоянно отдает остатки, и вы уменьшаете остаток, снижая его на время незавершенных резервов.
А в какой момент вы будете давать клиенту ответ?
Если клиент ждет пока статус документа не станет равен "зарезервировано", то вы просто изобрели свой WAL и поверх БД, у которой уже есть WAL. Ваш подход будет на порядок хуже использования транзакций.
Если клиент не ждет когда документ получит статус "зарезервировано", то я не понимаю как это должно работать. Предположим что у вас приложение, которое билеты в кино продает. Вы покупаете два билета, приложение вам говорит "Начато резервирование", так? А деньги когда списывать будет?