Стендап Сьогодні

Що я зробив, що я хочу зробити, і що це все значить.
Повсякденні здобутки в форматі стендапу.
Детальніше в статті

Підписатись на RSS
📢 Канал в Telegram @stendap_sogodni
🦣 @stendap_sogodni@shevtsov.me в Федиверсі

09.06.2023

PostgreSQL vs Elasticsearch

Поступив запит: чим Elasticsearch краще за PostgreSQL. Спробую сформулювати. Наперед скажу, що питання скоріше не чим, а де або для чого.

Постгрес — це база даних загального призначення. Вона вміє все. Та з кожною новою версією ще більше. Якщо порівнювати суто по можливостях, то з PostgreSQL можна робити що завгодно. В цьому його головна перевага. Якщо з чогось починати проєкт, то Постгрес найкращий вибір, завжди (якщо в бюджеті є місце для сервера бази даних, звісно.)

Єдине, що PostgreSQL робить гірше — це масштабується. Рішення для горизонтального масштабування існують, проте коли вертикальне (збільшення машини) не розв’язує задачу, то, на моєму досвіді, всі обирають поміняти базу. Наскільки вистачить однієї машини — залежить від того, що потрібно зберігати. Для облікових записів користувачів — напевно, вистачить назавжди. А для, скажімо, щосекундних аналітичних метрик — може й для старту буде мало. Бо як БД загального призначення, у PostgreSQL доволі обмежені здібності оптимізувати під задачу.

Як я вже писав, для вирішення сучасних потреб в масштабуванні зʼявилися бази даних NoSQL. В їхньому числі й Elasticsearch (так, як я вже писав, Elasticsearch - справжня база даних.) В серці кожної NoSQL бази сидить компроміс: так, вона масштабується, але характер використання буде обмежений. Тому, при виборі NoSQL бази, треба дуже уважно дивитись, що вона вміє, та чи не буде вам потрібно щось інше.

Elasticsearch вміє класний складний пошук та агрегації. При цьому його легко масштабувати як на запис, так і на читання. Як приклад того, що він робить погано: поєднання документів на кшталт JOIN. Тобто в базі мають сидіти документи, які нас цікавлять самі по собі.

Такий режим використання гарно себе показав для всілякої журнальної інформації, тому зараз більше можна побачити Elasticsearch як базу даних для журналів, ніж як пошуковий рушій (бо, якщо все, що вам потрібно — це повнотекстовий пошук — то його чудово вміє робити Postgres.)

На останнє, не раджу читати абстрактні порівняння вигляду “знайди 10 відмінностей”.  “PostgreSQL - реляційна база даних. Elasticsearch - документна” і так далі.  З таким підходом в сучасних базах (та й взагалі технологіях) швидко загубишся. Щоб обрати базу, треба розуміти, що вона робить краще інших, та може ще важливіше — чого ніяк не робить. А якщо є сумніви — беріть PostgreSQL. :)


08.06.2023

Кілька думок про Docker Compose

Сьогодні був день Docker Compose. Як я вже писав, в нас багато на нього навішано. Взагалі, як на мене, якщо вам доводиться працювати над системою складніше, ніж класичний LAMP-стек, то варто опанувати Docker Compose та відтворити на ньому архітектуру.


07.06.2023

Kafka

Тиждень тому я писав про важливість перенесення навантаження з критичного шляху. А також про те, що це вирішується чергами. Черга надає можливість передати роботу з одного сервісу до іншого. Але є проблема — черга це труба о двох кінцях. Нам обовʼязково доведеться створювати споживача “в пару”. Черга створює жорстку звʼязку сервісів.

Apache Kafka розв’язує цю проблему. Це дещо середнє між чергою та базою даних. Як в черзі, дані організовані в послідовність повідомлень. Як в базі даних, ці повідомлення надійно зберігаються миттєво після приймання, та не видаляються після їх прочитання та обробки. Категорія сервісів, до яких належить Kafka, називається брокер повідомлень. Один сервіс (або сервіси) повідомлення пише, інший (або інші) читають - все з надійним посередником посередині.

Як на мене, то в першу чергу Kafka корисна тим, що дозволяє високонавантаженому сервісу максимально швидко писати дані, без того, щоб відразу розробляти архітектуру їх обробки. Це й спрощує розробку, й підвищує надійність, і взагалі в наш час Big Data розкриває нові можливості збирати те, що незрозуміло як використати.

Але є й інші переваги. Kafka може роздавати одній й ті самі повідомлення декільком споживачам — наприклад, сьогодні вони потрібні тільки в базі, а завтра, може, зʼявиться сервіс аналітики.

Також є прості, але можливості обробляти дані всередині Кафки, наприклад, рахувати їх, або обчислювати кінцевий стан сутності по журналу змін - Kafka Streams. Та Kafka Connect - інструмент для завантаження даних з Кафки до звичайної бази даних або ще кудись.

Єдине, що мені не подобається — все воно написане на Java, з усіма особливостями конфігурації та розміщення сервісів на Java.


06.06.2023

Перша засада гарної доповіді — думай про аудиторію

Сьогодні слухав на роботі презентацію про те, як робити презентації. Причому фокус був на робочих дзвінках, які є повсякденністю для нас всіх. Задумався, які поради я можу додати зі свого боку.

На мою думку, головне, про що треба думати при плануванні доповіді (формальному плануванні, чи в голові за пʼять хвилин — це вже як піде) - це аудиторія. Бо предмет робочої доповіді нам зазвичай добре відомий. Але що з нього розказати? Я нерідко бачу, як люди закопуються в деталі, які нікому окрім них не зрозумілі, або навпаки, зазначають, що за два тижні рівно нічого цікавого не відбувалось. Тому, щоб підготувати себе, пропоную пару питань:

З таким фокусом в голові вже можна підходити до предмета доповіді та планувати, на яких аспектах можна зупинитись. А ще зорієнтованість на аудиторії сприяє рапорту більше, ніж правильний кут камери або уникнення слів-паразитів.

Раніше: про логічні ланцюги.


05.06.2023

Що робити з валютами

В продовження теми про зберігання фінансових значень, розповім трохи про валюти.

Наївне уявлення про валюти досить просте. Є одна валюта, є інша, є курс. Пазури програміста вже тягнуться до StackOverflow, щоб знайти там зручний API. Та й нескладно знайти багато джерел поточного курсу валюти. Є безплатні, є за підписку — гроші зазвичай беруть за частоту оновлень.

Проте така модель не проходить базової перевірки. Єдиного курсу валюти немає. Є міжнародний курс, є курс Нацбанку, є курс твого банку чи обмінника на куті. Який правильний? Відповіді немає. Точніше, реальний курс валюти існує тільки в момент обміну.

Тому що робити з валютою, залежить від конкретного застосунку та його бізнес-логіки. Якщо треба просто приблизно показати суму в іншій валюті — підійде один з API з курсами. Якщо це магазин — то у платіжної системи можна дізнатись точний курс. А якщо маємо справи зі справжніми банківськими операціями — то курс є властивістю операції та має бути вказаний явно.

В Сінтрі до розділу “Накопичення” валюта була суто косметичним елементом. Та поки не треба переводити з однієї валюти в іншу, цього достатньо. Але накопичення можливі не тільки в валюті бюджету, як всім нам знайомо. Ми вирішили під час створення внеску в накопичення відразу питати дві суми — скільки (умовно гривень) пішло з бюджету, та скільки (умовно євро) зайшло як внесок. З першого погляду, це можна було б автоматизувати, але насправді ні — коли відкладаєш гроші, потрібна реальна сума на руках, а ніяке не наближення.


04.06.2023

Зберігайте гроші в цілочисельних значеннях

Ми в Сінтрі зберігаємо всі грошові суми у цілочисельній формі, тобто як значення в копійках. Це важливо не тільки для проведення арифметичних операцій, а й для збереження та відтворення значень. Дробові числа ніколи не можна використовувати для точних обчислень, спробую пояснити, чому.

На перший наївно-освічений погляд, яка там різниця — адже 1.23 гривні це теж саме що й 123e-2, в науковій нотації. Але це тільки абстракція про людські очі. Насправді дробові числа зберігаються у двійковому вигляді, з двійковою експонентою, а ніяк не десятковою. (З 2008 існує десятковий стандарт, але на практиці його ніде не побачиш.)

Чому це має значення? Для цілих чисел двійкове зображення нічого не змінює, та ми можемо практично про нього не знати. Але з дробами все не те що гірше, воно дуже погано. Десяткові дроби, як правило, не перекладаються в красиві та акуратні двійкові дроби (пояснення виходить за рамки цього короткого оповідання.) Навпаки, типовий десятковий дріб стає періодичним двійковим. Так що ті 1.23 гривні у двійковій системі мають вигляд 1.00111010111.... При запису нескінченного дробу в скінченну памʼять ми обовʼязково втрачаємо точність.

При цьому при перетворенні округленого значення в десятковий вигляд ми можемо отримати вже інше значення: 1.23046875. Принаймні все двійкові дроби стають скінченними десятковими (хоча це мало нам допомагає.) Також добре, що такий десятковий дріб вже нормально вкладається у двійковий… якщо його не округлити в десятковому вигляді. Також точність втрачається на будь-якій арифметичній операції, навіть на додаванні.

Так на кожній операції значення поступово псуються, або, як то кажуть, гниють. Це не якесь теоретичне занепокоєння — ми стикнулись з ним вже на перших місяцях внутрішнього тестування. Після цього всю математику перевели на цілі числа, які стають дробами тільки для відображення їх в інтерфейсі.

Звісно, ми не можемо зберігати дробові значення копійок. Проте, як виявляється, реальні дробові копійки не існують. Та, хоч теоретично можна, скажімо, рівно поділити 1000 гривень на 7 днів та забюджетувати 142.85714286… на день, практично це не має жодного сенсу; фактично ми округляємо до 142.86 та коректуємо останній день, щоб вписатися в початкову суму.


03.06.2023

Поєднання HomeAssistant, Firebase та SwiftBar: коли системи працюють на тебе

Приємне: віддалений геймінг з Parsec працює краще, ніж я міг собі уявити. В локальній мережі з дротовим підключенням взагалі непомітно, що граєш віддалено. Але не тільки — навіть за 200 км від дому та по вайфаю все ще можна грати із задоволенням! Так, час від часу підключення гальмує, але достатньо рідко щоб це не шкодило. Рекомендую.

Є тільки одна проблема: той самий компʼютер може використовуватись й напряму. Та Parsec не пропонує способу дізнатись, чи зайнятий він, чи ні. Щоб уникнути незручних ситуацій, вирішив зробити для себе індикатор.

Тепер я можу легко перевірити, чи не зайнятий компʼютер, перед тим як підключатись в Parsec. І на це пішло небагато часу, бо рішення складалося з частин, що в мене вже були, та треба було тільки поєднати їх між собою.


02.06.2023

Корисні оповіщення

Сьогодні читав статтю DevEx: What Actually Drives Productivity та мою увагу звернув один проблемний робочий момент. Читав я тому, що чекав завершення задачі (в Terraform.) А коли вона завершиться — не знав; треба було не забути поглядати в термінал. Так можна забутися та надовго полишити роботу. В контексті статті — це поламаний Feedback loop.

Ба — та це ж ідеальна ситуація для застосування оповіщень! Нехай коли команда в терміналі завершується, то система мені нагадає. Я не люблю оповіщення, бо вони відвертають від роботи, але в цьому випадку навпаки, допоможуть до неї повернутись.

На щастя, я не перший таке придумав. Для моєї улюбленої оболонки fish є плагін done Для zsh є аналогічний zsh-notify, але я сам не перевіряв. Ще VSCode вміє видавати звуки на закінчення команди, та мені віконце оповіщення більш до вподоби.

До речі, самі оповіщення уможливлює утиліта terminal-notifier, яку можна легко застосувати у своїх скриптах. Єдине, що вона потроху старіє, а надійної заміни я не бачу.

Взагалі цікава стаття, на мою думку кожна команда може сформувати для себе набір KPI-індикаторів, щоб не ходити по колу нескінченних проблем на кшталт “доводиться довго чекати схвалення ПРів”, які виправляються, та через місяць-два підіймаються наново. Якби були показники, то можна стежити постійно та не доводити до критичного стану.


01.06.2023

Коротке розслідування в те, як Facebook збирає інформацію

Цікава подія трапилася: показав дружині крісло (до речі, безплатна реклама - home-club.com.ua - надійний спосіб замовити щось з Ікеї в Україні.) А ввечері то саме крісло зʼявилося у дружини в рекламі на Фейсбуці. При тому, що показував я на своєму компʼютері та ніякої очевидної передачі даних не було.

Що за екстрасенсорні здатності проявляє фейсбук в цьому випадку? Чи почув нашу розмову, наприклад? Мені здається, можна пояснити й простішими технологіями.

На сторінках Home-Club є скрипт фейсбуку. (Що логічно, раз вони запускають там рекламу.) Тобто фейсбук знає, що я дивлюся цю сторінку. Але до чого тут дружина? Тут є нюанс. Я взагалі фейсбуком не користуюся та активного сеансу не маю. Тому приєднати відвідування сторінки до мене не вийде. Але ж на той самій домашній IP адресі сидить дружина. На мою думку, тому подія записується на той обліковий запис, що можна привʼязати до IP адреси, та далі сприяє появі товару в рекламі.

Я б хотів звернути увагу на те, що збір аналітики йде далі, ніж просто “записати, які сторінки ти відвідував”. Вони збирають максимум даних та колупаються в них, щоб вичавити корисну інформацію. Щоб запобігти цьому, треба користуватись блокувальником трекерів та реклами (реклама та трекери йдуть рука об руку.)

До речі, в мене взагалі мають бути заблоковані всі трекери, аж два рази — або вбудованим захистом Safari, або 1Blocker. Але з усім тим вкладка “Мережа” інструментів розробника чітко вказувала на взаємодію з фейсбуком. Виявилось, що після оновлення 1Blocker необхідно відкрити один раз сам додаток, щоб він завантажив правила. Бо сучасні блокувальники реклами не втручаються в роботу браузера, а передають йому інструкції про те, які ресурси блокувати. Такий підхід практично не витрачає додаткових ресурсів.


31.05.2023

Оптимізація критичного шляху

Трохи міркувань з приводу дизайну архітектури навколо критичного шляху. Це така ділянка коду, який викликається найчастіше та містить головну бізнес-логіку вашого сервісу. Наприклад, в Телеграмі критичний шлях — це відправлення повідомлення. Чи є він у вас? Варто замислитись, якщо не знаєте.

На останок, не треба всього цього робити з MVP. Достатньо заздалегідь усвідомити, де той критичний шлях пролягатиме. Окрім витрат на передчасну оптимізацію, доробляти вже зоптимізований код завжди складніше.