Типичный программист
✔
78.1K subscribers
3.81K photos
1.16K videos
14 files
8.46K links
Всё самое интересное по программированию

Разместить рекламу: @tproger_sales_bot

Правила общения: https://tprg.ru/rules

Другие каналы: @tproger_channels

Сайт: https://tprg.ru/site

VK: vk.com/tproger

Регистрация в перечне РКН: https://tprg.ru/mJwo
Download Telegram
Миллион запросов в секунду мимо общего балансировщика

Сто микросекунд задержки выглядят мелочью. Пока один запрос не превращается в сотню параллельных: ответ придёт, когда закончит самый медленный. У Zalando эти обращения ещё и проходили через общий Skipper. При скачках задержки было трудно понять, кто виноват: сервис или чужая инфраструктура.

Команда перенесла выбор узла внутрь вызывающего процесса. Пришлось точно повторить прежнее хеш-кольцо, чтобы товары попадали в те же кеши. Переходили постепенно, сохранив обратный путь через Skipper на случай проблем.

На пике напрямую пошло больше миллиона запросов в секунду. По данным команды, задержки стабилизировались, а парк Skipper для этих маршрутов сократился с 50+ копий до восьми. Сам Skipper никуда не делся: внешние запросы остались у него. Тут убрали один лишний круг внутри системы, а не переписали весь входной трафик.
🤔3👏2🎉2❤1🔥1😘1
Forwarded from 
This media is not supported in your browser
VIEW IN TELEGRAM
Gran Turismo 4 переехала в Chrome — с гонками, звуком и сохранениями

В PS2 Web Recomp старые игры запускают прямо во вкладке. Gran Turismo 4 проходит меню и гонки, играет музыку и сохраняет прогресс в браузере. По замерам автора, PAL-версия держит 50 FPS в Chrome на встроенной графике ноутбука при удвоенном разрешении PS2.

Машинный код игры заранее переводят в C++, затем собирают в WebAssembly. Графику рисует WebGPU, а окружение воспроизводит нужные части системы и железа PS2. После Gran Turismo автор запустил God of War II: вторая игра помогла найти ошибки, которых первая не замечала.

📎 В репозитории проекта есть код, скрипты сборки и подробности оптимизации. Готового каталога игр здесь нет: понадобится свой образ диска, который скрипты превратят в локальную веб-страницу.
Please open Telegram to view this post
VIEW IN TELEGRAM
👍10🔥4😁3❤‍🔥2☃1🤔1🤩1💔1💋1😈1👀1
Сжатие временных рядов в Axiom: меньше места на диске, больше работы процессору

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

Новые измерения попадают в несжатый буфер, где их сортируют по времени. Заполненный буфер сжимают пакетом и переносят в сжатую часть. Время отмечают битовой картой: каждый установленный бит указывает на момент с измерением. При запросе карта помогает выбирать точки из нужного диапазона.

На данных Axiom хранилище обычно занимает 30–50% от размера Gorilla. Но оптимизированная Gorilla примерно в 15 раз эффективнее по CPU, то есть затратам процессора на кеш. Память кеша чаще составляет 70–100% от Gorilla; все цифры зависят от нагрузки.

#облака
❤6👏5👍2🗿2⚡1🔥1😐1🙈1🤗1🫡1👾1
Forwarded from 
Вебинар в прямом эфире уже идёт десять минут. Вы только открыли трансляцию. Что для вас важнее всего?
Anonymous Poll
13%
Минимальная задержка от живого момента.
10%
Стабильное разрешение картинки.
14%
Ровный звук.
62%
Возможность отмотать назад и вернуться в эфир.
🤨5🔥2🥰1😱1😢1🎉1🐳1😈1😇1🗿1😎1
Пять лет новых функций. Сколько памяти теперь ест libcurl?

Обычно от такого сравнения ждёшь грустного графика. Дэниел Стенберг, автор curl, сопоставил libcurl 7.75.0 и 8.19.0-DEV и получил смешанную картину: структура одного соединения уменьшилась с 1472 до 912 байт, а две другие выросли.

Для десяти передач и двадцати открытых соединений сумма этих трёх структур оказалась на 10 000 байт меньше. Но при скачивании одного файла на 512 МБ пик памяти вырос на 1,6%, а число аллокаций увеличилось с 96 до 107. Один красивый показатель тут легко спрятал бы второй.

В тестах curl теперь есть проверка размеров пятнадцати важных структур. Превысил лимит — сборка упала, дальше приходится объяснять рост. Замеры Стенберга сделаны на Linux с HTTP без TLS. Память криптографической библиотеки в эту историю не входит.
👍6🔥4❤2🤔2👏1😁1
Forwarded from Типичный программист
Общая папка для работы Claude Code и Codex

Луи-Франсуа Бушар собрал заметки, инструкции-скиллы, скрипты и итоги встреч в Obsidian. Его связка устроена так:

Папка хранит исходные материалы и решения
↓
Индекс указывает, где искать данные для задачи
↓
Claude Code планирует работу
↓
Codex выполняет задачи по его вызову

В описании этого рабочего процесса Бушар объясняет, зачем даёт агенту сведения для конкретной задачи. Начать предлагает с общей папки, короткого индекса и одного повторно используемого скилла.

#ии #инструменты
👎4🤔3❤2👍1👏1😁1🎉1💯1👻1🤝1💊1
Сортировку ускорили в 26 раз. Общий алгоритм просто знал слишком мало

У Axiom разные колонки сортировались одинаково: сравнивали значения по два, каждый раз превращая их во внутренний общий тип. Удобно. Только колонка с уровнями логов уже знала, что разных значений в ней не больше пятнадцати. А сортировка этой подсказкой не пользовалась.

Команда дала каждому типу колонки свою реализацию. Для enum сначала упорядочили небольшой словарь, затем разложили строки по счётчикам. Для строк начали сортировать ранги словаря, не сравнивая один и тот же текст снова и снова.

На блоках примерно по 65 тысяч строк, на Apple M4, ускорение разных типов составило 2–26 раз. Максимум достался enum. Это не обещание ускорить любую сортировку: выигрыш появился там, где данные уже имели полезную структуру. Её не пришлось придумывать, достаточно было перестать терять при каждом сравнении.
❤3👍3🎄3👏2🎉2😇2🫡2❤‍🔥1😱1🐳1😭1
Завтра иду на GoCloud Tech 2026

Кому интересно узнать какие-нибудь подробности с мероприятия? Могу потом рассказать отдельно!

И, конечно, можем увидеться там, если вы тоже идёте.
🔥10👎6👏3👌3🍾2😁1🐳1💅1🤪1🆒1🙉1
Python обработал 7,6 ГБ JSON за 0,12 секунды

Здесь интересно, куда уходило время. Дэниел Лемир, исследователь производительности, взял 2,2 млн событий GitHub, чтобы посчитать открытые PR по языкам. А Python при обычном разборе создавал кучу словарей, списков и строк, которые для этой задачи вообще не нужны.

В эксперименте с fastsimdjson и lazy=True Python-объекты создаются только для запрошенных полей. Сборка Python без GIL позволяет обрабатывать события в 64 потоках внутри одного процесса. У каждого потока свои счётчики, в конце их складывают. Зачем собирать весь объект, если нужна только малая часть?

У Лемира получилось около 0,12 секунды. Стенд: два Xeon Gold 6548N, 64 ядра, free-threaded Python 3.14.6 и fastsimdjson 0.6.0. Все 7,6 ГБ уже распакованы в RAM, чтение с диска и распаковка в замер не входят. Это лучший из семи прогонов, одинаковую статистику сверили всеми методами.
❤14👍12🤣8🎉3👀2🤯1😍1🌚1🌭1🤝1🫡1
Зачем Figma рисует невидимый HTML рядом с холстом

На холсте Figma может быть сотня слоёв, а для экранного диктора всё это долго выглядело как один большой объект. Рисование взял на себя движок Figma. Вместе с ним исчезла и привычная HTML-структура, по которой браузер объясняет интерфейс человеку.

Команда собрала Mirror DOM: невидимые элементы с ролями, подписями и расположением слоёв. Между ними и холстом синхронизируют фокус. Выбрали объект мышью — диктор знает, где вы. Перешли диктором к другому элементу — выделение на холсте тоже поменялось.

И невидимое здесь не значит убранное в угол экрана. Элементам сохраняют реальную геометрию: она нужна лупе, подсветке фокуса и голосовому управлению. Даже пять сдвигов по одному пикселю объединяют в одно объявление, чтобы диктор не повторял одно и то же пять раз. Вот сколько поведения браузера пришлось вернуть вручную.
🔥7⚡6👏3😱3🏆2😈2🎄2🤷‍♂1💔1🎅1💊1
Историю звёзд GitHub собирали за 2500 запросов. Теперь хватает 24

Чтобы построить график популярности React, сервису приходилось выкачать около 251 тысячи пользователей, оставить даты и выбросить имена. Плюс каждый запрос заново пересчитывал все звёзды ради пагинации.

В новом API GitHub возвращаются дневные счётчики. Но одного GROUP BY мало: если сначала сгруппировать всю историю и только потом применить LIMIT, база всё равно сделает лишнюю работу.

Поэтому запрос сначала выбирает индексированный диапазон дат, затем считает звёзды внутри него. Одна страница покрывает до 30 недель; для React вся история укладывается примерно в 24 запроса.

Очень плотная неделя ещё может дать дорогой запрос. И это история оставшихся звёзд: снятые звёзды в исходной модели не сохраняются.
❤4👍3👌2🏆2😎2🤔1😢1🤩1🌭1🙈1🙉1
Баг появлялся в 0,001% случаев. Виноваты оказались два формата одного ответа

MySQL-запрос иногда возвращал пустой результат вместо строк. В Hyperdrive ошибка возникала только с включённым кешем, а поймать её трассировкой долго не удавалось.

У Cloudflare нашлось объяснение: два узла могли пользоваться общим кешем, но записывали туда разные байты. Один сохранял ответ в формате Hyperdrive, другой — уже преобразованный под возможности клиентского драйвера.

Разница касалась пакетов EOF и OK, обозначающих границы результата. Чужая версия ответа могла выглядеть как преждевременный конец данных или приводить к зависанию.

Исправление: всегда хранить в кеше один канонический формат, а преобразование выполнять перед отправкой клиенту. После этого проблема с пустыми ответами исчезла.
❤8👍5🔥5😈3☃2😐2🤷‍♂1👏1🌭1🍾1👻1
«Повторим запрос один раз» может превратиться в восемь запросов

Представьте цепочку A → B → C → D. Если D ошибается, а каждый предыдущий сервис повторяет вызов один раз, до D в худшем случае дойдут восемь попыток на один исходный запрос.

Лимиты ретраев уменьшают усиление, но оно всё ещё накапливается по цепочке. В Uber добавили контекст ошибки: инфраструктура различает сервис, где она возникла, и сервисы, которые лишь передают её выше.

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

Так временный сбой сохраняет шанс на успешную повторную попытку, а перегруженный сервис не получает дополнительную лавину от каждого уровня зависимостей.
👍9🤗5✍3💘3😎2⚡1🎉1🤨1😴1👻1💅1
Закрыл тело HTTP-ответа — и неожиданно ускорил следующие запросы

В примере из блога Go программа сто раз получает HTTP-статус, не читая тело. С HTTP/1 на машине автора это занимает около 710 мс в Go 1.26 и 150 мс в Go 1.27.

Причина — повторное использование соединений. В HTTP/1 нужно дочитать текущий ответ, чтобы найти начало следующего. Раньше закрытие непрочитанного тела приводило к потере соединения для повторного использования.

В Go 1.27 net/http.Transport пробует дочитать остаток в фоне: не больше 256 КБ и 50 мс. Если успевает, соединение можно вернуть в пул. Приложению по-прежнему нужно вызвать resp.Body.Close().

Ускорение зависит от размера ответа и сети. Для HTTP/2 такая процедура дочитывания не нужна: там запросы используют отдельные потоки.
❤11🤔3😁2👌2😇2🍌1👀1🆒1💘1🙉1👾1
Почему разработчики Rust всё ещё выбирают print

Команда Rust опросила больше 2300 человек об отладке. Более 46% участников сейчас пользуются дебаггером. При этом логи, печать и dbg! остаются привычными инструментами.

Самая частая причина отказаться от дебаггера в конкретной ситуации — через вывод разобраться быстрее или проще. Её указали чуть больше 81% ответивших на этот вопрос.

Есть и проблемы инструментов: значения показываются неудобно, переменные не удаётся вывести, пошаговое выполнение спотыкается об async и макросы. Вместо содержимого HashMap можно получить устройство её внутренностей.

Среди направлений улучшения — визуализация типов и коллекций, async-стеки и документация по настройке. Это ответы участников добровольного опроса, а не перепись всех Rust-разработчиков.
👍8💯4❤‍🔥2🔥2🤨2🥰1🤔1🎉1👌1💔1😨1
Void объединяет Vite-приложение и его инфраструктуру

Уже есть фронтенд. Теперь нужны серверные маршруты, база, авторизация и место, куда всё это выложить. Void от Cloudflare собирает эти части в общий рабочий процесс.

В проект входят SDK, CLI и открытая платформа развёртывания. SDK работает как плагин Vite, CLI выделяет необходимые ресурсы, а платформу можно развернуть в аккаунте компании.

Администратор задаёт доступ и ограничения ресурсов; разработчики выкладывают приложения через общий сервис. В SDK есть маршруты API и передача типов от запроса к базе до интерфейса, а также интеграции с существующими фреймворками.

Для собственной платформы нужны Workers for Platforms, R2, PostgreSQL, провайдер входа и домен. Открытый код позволяет адаптировать её, но готовый сценарий развёртывания построен вокруг Cloudflare.
❤4🤔4👨‍💻4🔥2💊2✍1👎1🤣1😇1💅1🦄1
Конкурентные записи разрешили. Все всё равно стояли в очереди на диск

В Turso 0.7 несколько транзакций уже могли работать параллельно. Но при фиксации каждая отдельно ждала fsync: подтверждения, что изменения записаны на диск.

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

Group commit позволяет нескольким транзакциям разделить одну синхронизацию. Подтверждение приходит после сохранения нужной части журнала; требование надёжности записи остаётся.

Выигрыш появляется при конкурентных записях: становится больше работы на один дорогой поход к диску. Для одиночного последовательного клиента такая очередь почти не набирается, поэтому ждать того же ускорения не стоит.
🎉3❤2👏2👌2🎅2☃1🍓1😭1😨1🫡1🎄1
Байесовский A/B-тест тоже можно остановить неправильно

Проверять эксперимент каждый час и выключать, как только новая кнопка «побеждает», заманчиво. Но переключатель Bayesian в интерфейсе сам по себе не гарантирует контроль ложных находок.

В Spotify разобрали разные конфигурации: априорное распределение, модель данных и правило остановки работают вместе. Плоское априорное распределение с остановкой по порогу вероятности может воспроизвести проблему постоянного подглядывания в обычном тесте.

Есть байесовские методы, которые контролируют ошибки при такой проверке, например остановка по Bayes factor. А информативный prior может улучшить оценку эффекта — если он действительно подходит новым экспериментам.

Spotify пока не видит необходимости добавлять Bayesian-режим к своим инструментам. Выбор метода здесь начинается с требуемых гарантий и цены ошибок.
🗿4👍2❤1👏1😁1🕊1💯1🍾1😈1🎅1🙉1
SIMD в Go: сложные инструкции спрятали за обычными методами

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

В экспериментальном `simd/archsimd` Go 1.27 к amd64 добавились arm64 и wasm. API включается через GOEXPERIMENT=simd и позволяет обращаться к возможностям конкретной архитектуры из Go.

Названия не копируют длинные имена инструкций. Сложение выглядит как x.Add(y), а операция с маской — как x.Add(y).Masked(m). Компилятор может свести такое выражение к подходящей машинной инструкции.

Это уменьшает число специальных методов и оставляет оптимизатору часть работы. Но API экспериментальный, набор операций зависит от архитектуры, а выигрыш нужно проверять на своём алгоритме и процессоре.
❤5🎉3👏2🍌2💋2🙊2😁1😭1👻1👨‍💻1🙉1