• Хватит выгорать

    Давно хотел написать пост про выгорания. Не буду ходить вокруг да около.

    Ребята, хватит выгорать. Перестаньте это делать. Не выгорайте.

    Не читайте статей про выгорание. Не пишите сочувствующие комментарии. Это как удобрять сорняки.

    Выгорание стало модным. Все выгорают. Откроешь Твиттер, Хабр, а там — этот устал, другой выгорел, третий, четвертый…

    Хватит уже.

    Достаточно одной громкой статьи, и пожалуйста. Ее читают тысячи молодых людей, и у каждого срабатывает эффект “это про меня”. Это старый, как мир, принцип, когда человек примеряет на себя прочитанное.

    Это было еще в “Трое в лодке”:

    Это поразительно, но всякий раз, когда я читаю объявление о каком-нибудь патентованном лекарстве, мне приходится сделать вывод, что я страдаю именно той болезнью, о которой в нем говорится, и притом в наиболее злокачественной форме. Диагноз в каждом случае точно совпадает со всеми моими ощущениями.

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

    Счастливым, здоровым человеком вошел я в эту читальню, а вышел из нее разбитым инвалидом.

    Заканчиваешь читать подобную статью, и думаешь: это же обо мне! На работе не прет, поссорился с близкими, устал… черт, Я ЖЕ ВЫГОРЕЛ! Все, как в интернете написано. Чувак, сочувствую! У меня то же самое!

    Где-то в интернете лежит смешной текст. Обычный человек разговаривает со Вселенной. Жалуется на проблемы: тяжело на работе, не понимают родители, разлад с половинкой… Словом, типовой набор, через который проходят все. А Вселенная слушает с гротескным вниманием, кивает, поддакивает.

    Не понимают родители? Никогда такого не слышала. Ах, на работе не получается? Это первый случай в моей практике. Вы слышали, ему тяжело! Миллионы лет не было такого, и вдруг! Все для тебя сделаю, дорогой. Поставлю на паузу процессы, остановлю время и займусь лично.

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

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

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

    Заболел — лечись. Если видишь, что все плохо, то почему сидишь на пятой точке полгода, пока не станет хуже? Почему не меняешь работу, не заводишь новых друзей, не меняешь деятельность?

    Я работаю с 17 лет, но ни разу не выгорал. Где только ни бывал. На телевидении, в типографии, в газете, в веб-студии, в госконторе, в аутсорсе… Бывало разное: и дико перло, и люто бомбило. Но никогда не было свинцового уныния и желания ныть. Пожаловался раз, выпустил пар — и дальше.

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

    Читаешь кого-то: все, выгорел, больше никогда и на за что. Через месяц — как ни в чем не бывало занимается тем, чем раньше. Чувак, ты просто устал. Отдохни, сделай паузу в два месяца между проектами. Съезди куда, книжки художественные почитай. Перестань кодить по ночам, спи по девять часов, принимай ванны.

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

    Теперь по аналогии. Ночью ты задрачиваешь Хаскель, днем вареный пишешь на кровавой Джаве, кофе и сигареты каждые полчаса, под вечер возбуждение и опять ночь перед монитором. Прибавьте сюда опенсорс. Как же тут не устать? Но это усталость, а не выгорание. А причина усталости — отсутствие режима и лень следить за собой.

    Не надо этих постов, что выгорел. Ты отравляешь мозг молодым и неопытным. За очередным постом про выгорание нет ничего, кроме инфантильного нарциссизма, упоения страданием.

    И не стоит чрезмерно себя жалеть. Жизнь — это тоже трудности. Преодолевать усталость и тоску — нормально.

  • Код картинкой

    Раньше я считал, что постить код картинкой это отстой и днище. А теперь наоборот — частенько набрасываю в чат скриншоты с Гитхаба и совершенно не вижу криминала.

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

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

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

    Read more →

  • Не надо таких подарков

    Удивляет, что фирмы так и не научились дарить что-то нормальное клиентам. Не подумайте, что мне что-то нужно, мне и так хорошо. Просто негативный осадок. Если взялись дарить, так дарите нормально, а не как импотенты.

    Пришло письмо от Тинькова — мой милый, хороший, у тебя ДР, держи подарок: две книги на Литресе. Хорошо, как раз хотел прикупить кое-что. Но оказывается, выбрать можно только из ограниченного набора книг, из которого мне не подходит ни одна.

    Это бесит. Почему нельзя выбрать любую? Почему должен выбирать только из говна? Что вы за импотенты такие? Дарить так дарить! Подписался — делай нормально! Это как отвести ребенка в ТЦ на день рождения и сказать — ни в чем себе не отказывай, но сумма в чеке не должна превышать 500 рублей. Родитель-днище.

    И везде такое говно. Баллы, которые сгорают через неделю. Бонусы, которые действуют только три дня спустя две недели покупки. Пока распаршу такие требования, уже становится нехорошо. Сраные сертификаты, которыми можно оплатить только треть покупки. Хватит, наелся ваших подарков.

    Стоит заметить, что с материальными подарками дела обстоят лучше. Тот же Тиньков вместе с картой Airlines прислал наборчик путешественника. Плед, носки и маску для сна. Маска особенно зашла, я до сих пор в ней сплю. А вот с цифровыми подарками беда, хотя казалось бы — данные в базе подвигать.

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

  • Девочки

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

    У слова “девочка” есть только одно нормальное значение — человек женского пола до подросткового возраста. Потом идут девушка, женщина, бабушка или старушка. Они — не девочки.

    Вот это, например, девочка:

    Read more →

  • Триал

    На триал-версию программы должно распространяться простое правило. Ее всегда можно открыть, чтобы принять финальное решение о покупке.

    На картинке выше неудачный триал Final Cut, программы видеомонтажа. Я поставил ее месяц назад и один раз запустил. Потом что-то меня отвлекло, и больше программу я не открывал.

    На праздниках появилось время, сел монтировать видео и снова вспомнил. Думаю, открою, погоняю туда-сюда и, скорее всего, куплю. Но фигушки — неделя триала кончилась. Раньше надо было. Или идешь лесом, или покупаешь кота в мешке.

    Очень, очень странная политика! Предположим, я подошел к продавцу, посмотрел товар, но не купил. Подошел повторно, прошу показать еще раз, а мне в ответ — нечего смотреть, или покупай, или проваливай. Сегодня даже на рынке так себя не ведут, это какой-то колхоз. А почему-то в интернет-торговле считается норм.

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

    Правильно делать так: триал-программа всегда запускается, но работает с ограничениями. Например, Lightworks, программа промышленного видеомонтажа, без покупки лицензии имеет только одно ограничение — не позволяет сгонять проект в разрешении свыше 720 линий. Производитель ничего не теряет: для любителей программа слишком сложна, для профессионалов разрешения 720 недостаточно. Можно работать месяцами, полностью изучить программу перед покупкой.

    Другой пример — Wing IDE для разработчиков на Python. По истечении триала программа запускается на 10 минут, после чего сама себя завершает. Это тоже норм, потому что остается возможность ее исследовать.

    Редактор Sublime Text время от времени показывает блокирующий алерт. Это не проблема, если запускаешь его раз в месяц. Но сильно раздражает, если используешь его как основной инструмент разработки. Так или иначе, он запускается всегда, и есть возможность подумать.

    Если вы причастны к разработке триал-версии продукта, никогда не поступайте как Final Cut. Нельзя разворачивать пользователя по истечению срока. Пользователь не обязан все бросить и посвятить неделю исключительно вашей программе. У него дела, авралы, дедлайны. Программа должна ограничивать не время работы, а возможности: форматы, расширения, объем файлов. Но запускаться она должна всегда.

  • Реактивный митап

    Провели очередную встречу в клубе Глубокого Рефакторинга. На этот раз вели базары за Реакт и мобильную разработку.

    React через призму функционального программирования, Антон Чикин:

    Мобильная разработка на React Native + ClojureScript, ваш покорный слуга:

  • Дамп Телеграма

    Обленился, некоторое время писал в Телеграм. Дублирую наиболее осмысленные посты.


    Бывает, вы восхищаетесь чьим-то мастерством и выражаете удивление. Как ты так научился? А он такой — да фигня, это легко.

    Это называется кокетство, легкое заигрываение. Вроде как нельзя согласится и приходится врать. Такой уж этикет.

    Кокетство не отменяет правды. Скорей всего, человек сильно вложился во что-то, и теперь оно действительно для него легко. Но процесс вкладывания был офигенно трудным.

    Этим объясняются отговорки про талант и наследственность. Они лишь малая часть, а основное это труд, пока другие расслабляются. Ну и зависть как сайд-эффект, потому что на старте вы были на равных.

    Ничего не бывает легким.


    Современные дети на голову лучше нас. Во всем.

    Они не курят за гаражами. Мальчики не хватают девочек за косички. Они не потребляют трешак, который наводнил РФ в перестройку. Они умнее, они пользуются гаджетами с малых лет. Для них миллион кружков и секций для всех возрастов. Им интересно жить. Для них делают прекрасные познавательные мульты и фильмы о космосе и природе. Вся детская медия направлена на гуманизм. Это прекрасно.

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


    Прихожу я в школу на собрание и слышу все то же говно. МЫ НЕ УСПЕВАЕМ, конец полугодия, еще не прошли это, ШКОЛЬНАЯ ПРОГРАММА, времени нет, ДЕТИ НЕ ПОНИМАЮТ, ленивые, ОДНИ ГАДЖЕТЫ, ааааа!

    Чем кончаются проекты, где никто ничего не успевает? Плохо они кончаются, все это знают. Хроническое неуспевание надо лечить на уровне менеджмента и планирования.

    А не стараться все успеть годами!

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


    Столкнулся с тем, что физически не могу смотреть видосы с закадровым смехом. Противно до тошноты. Мой внутренний смех никогда не совпадает с тем, что в кадре. Зрительский смех вставляют в самых банальных, плоских моментах, когда я и не улыбнусь. И никогда там, где действительно смешно. Из-за этого кажется, что сидишь в окружении дебилов, и весь кайф уходит.


    В самолете со мной сидела девушка. Волосы цвета моркови, пирсинг, тату. Но насторожило меня не это.

    Девушка изображала иностранку. На вопросы стюардессы отвечала Yes, No и Sorry. Переписывалась в телефоне на английском. Но беглого взгляда хватило, чтобы заметить: собеседника зовут Глеб (кириллицей). Очень маловероятно, что нейтив инглиш спикер забьет в контакты “Глеб”, а не “Gleb”.

    Ладно, может, это собеседник так назвался, а мессаджер показывает как есть? Но в тексте полно ошибок уровня пре-интермедиейт. “I not understand” — путает am и do (состояние и действие). “He go, she say” (теряет -s/es в глаголах второго лица).

    А когда у девушки упал рюкзак, она на чистом русском сказала “ой!”. Не оу, не ауч, а наш чистый ой.

    Зачем это, интересно? И летел-то я провинциальным рейсом из Воронежа в нерезиновую. Может, это такой способ вжиться в образ, чтобы изучить язык?


    Просто всякая хрень про Лозанну, Швейцария.

    Выключатели делают не снаружи, а внутри. То есть сначала заходишь в темное помещение, и только потом включаешь свет. Странно. Зато почти каждый выключатель — розетка. Клево. Выключатели в основном кнопочные.

    Поражает устройство улиц. Нет бордюров, все плоское. Там, где нельзя парковаться, ставят громадные камни. И красиво, и полезно. Пешеходные переходы совмещают функцию лежачего полицейского.

    Все здания построены вровень с землей. Не бывает порогов. И не надо лечить про сложный рельеф в России! Я в городе на берегу озера, все стоит на спуске. При этом любая дверь вровень землей.

    Опять про о спуск. Если сразу много лестниц, то ставят лифт. Я оценил, когда шел с сумками из магазина. Лифт нужен всем, независимо от возраста и здоровья.

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

    В западной части страны все фигачат на французском. При этом пишут на немецком, потому что он преобладает по стране. Но не разу не слышал здесь немецкий. Английский знают в достаточной мере все. Люто завидую чувакам, которые переключаются мгновенно. Со мной по-английски, по телефону по-французски.

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


    Еще давно прочитал в чьих-то записках эмигранта, что в Швеции нельзя спускать унитаз ночью — пожалуются на шум. Хоть я и в Швейцарии и за унитаз ничего не говорят, это похоже на правду. Люди очень ревностно относятся к тишине.

    Понятно, я не мог обойти все дома, поэтому сужу по подъезду, где живу. Сразу на входе написано, что шуметь нельзя. На дверях висят объявления с указанием часов, когда их ребенок спит. Некоторые семьи просто лепят на двери рисунки детей. Как я понял, это сигнал. Здесь ребенок, не шуметь.

    Климат в Швейцарии мягкий, поэтому стены тонкие. В квартирах слышно все. Звук телевизора, игры детей. Когда работате душ, кажется, что за окном дождь. В 6 утра слышно, как кто-то крадется в туалет.

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


    Отличная цитата:

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


    И еще одна деталь, которая бросается в глаза русскому путешественнику. В Европе чаще видишь женщин там, где их нет в России. Или тех возрастов, где у нас только молодые.

    Сеогдня, например, видел женщину-рабочую, которая разгружала грузовик. Все делали краном, труд автоматизирован. Она не таскала мешки на своем горбу. Так почему бы и нет?

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

    В любом самолете, который летит в Европу, среди экипажа будет женщина старше сорока. А может и под полтинник, если учесть, как они за собой следят. И это норм. Нельзя выкидывать человека с работы только потому, что поседели волосы и стало больше морщин.

    Можно смеяться над этим и постить смешные картинки, но факт остается. Россия — довольно отсталая страна в вопросах возраста и пола.


    Этот коммент сделал мой день:

    мой односельчанин купил квадрик за 100 тысич и там камера 4 к

    Здесь прекрасно все от начала до конца. Минимальная емкость, но какой плотный контекст, понимаете? Каждое слово на вес золота. И односельчанин, и камера, и орфография, и вообще. Вот она, жизнь. Люблю такое.

  • Такое

    В интернете модно говорить “это такое…” с томной затяжкой на конце.

    • Ездить через всю Москву — это такое…
    • Писать под мобилу на Джаваскрипте — это такое…
    • Косплеить Соню Блейд без сисек — это такое…

    Что это, откуда пришло? Такое — что именно? Говно? Ну так договаривай!

    Говорить “это такое” — это такое…

  • I will never let monads be in a Clojure project

    Sounds a bit aggressive, doesn’t it? Well, let me explain. Monads are fine while you’re playing with them in Haskell. But don’t bring them to Clojure. They are completely foreign beings to Clojure ecosystem. Besides the technical issues, there is a problem with sharing monads across the team. Read the following, and I hope you’ll get into what I’m worried about.

    Nobody uses monads in libraries

    So, why you’d better not to ship monads into Clojure code? First, they are used quite rarely in production. Let me open my recent project which is just another two-in-one boring stuff. An HTTP server plus a single page application. I’ve got plenty of dependencies here in my project.clj file. There are about 40 of them just to cover basic stuff. Database, oAuth, UI… I don’t want to dump the whole list here. Check this gist for the reference.

    The full tree of dependencies expands into multiple screens. Their children libraries, and their children, and so forth. There are about 100 packages in total.

    Now guess how many of them use monads? You know that, it’s zero. None of the libraries needs monads to bear their functionality. I’d like to stress that. Some of them provide a really tough stuff: database access, template system, HTTP communication, etc. Yet they work without monadic operations. Why? Just because Clojure is powerful enough. It brings everything you need for convenient development. The authors of those libraries didn’t use monads not because they are not aware of them but because they just don’t need them.

    I don’t believe you are experiencing a trouble which is much more serious then something mentioned above and thus craves for monads. There is definitely a plain way for doing this.

    Railway Programming is a toy

    Moving on, most of the people who are using monads told me, they are fascinated with the idea of Railway Programming. I believe you are aware of this site and their mental model in general. Several years ago I fell into it completely thinking I’ve found the ultimate solution. It didn’t work, I regret to say.

    The problem with it is, it’s just a mock. A toy model which looks nice on the screen. At first glance, it reminds a holy grail that you’ve been looking for years and got it finally. So simple: just cut your code into a set of same looking chunks and then build a pipeline.

    I’ve been praying for that picture for months.

    Suddenly, it becomes clumsy and tough once you try to fit it into a real project. You’ve got to write more code. As I mentioned, none of the libraries really use it. All the functions should be wrapped to return monadic values rather than plain ones.

    The standard let, cond, when, and dozens of useful core functions don’t work with monadic values. You’ll lose a huge stuff for no reason. Instead, you’ll have to implement monadic versions of let, if, etc. Then test them, write documentation. Why? It’s clear to me, the more code you’ve brought on board, the less the project is maintainable.

    We are already there

    The Railway Programming proposes a happy path where each step leads either to the next happy step or to the negative outcome. This is fine, but we’ve already got the same stuff, indeed. These are exceptions. They act the same way.

    Take a look at the standard Railway example. They query the database, send email, write a file, etc. Surely, each of these steps is dangerous, whoever argues. But I don’t see a reason for why not to wrap the whole code with a simple try-catch statement? It acts exactly the same. For example, when an error occurs on the third step which is sending email, the entire pipeline terminates so we end up in the catch clause.

    Here, we’ve got an exception instance with most of the data we need. What to do next is up to us. We can log the error and fail silently. Or rise another exception with a high-detailed message plus the source exception attached for a cause. That’s is sufficient for maintaining the business logic.

    The main reason people turn to monads is, they’ve got lack of knowledge of using exceptions. There is no common rule for handling exceptions and thus it might be tricky sometimes. Some of them must be caught right here, others should flow up. For example, when iterating through the list, I wouldn’t like to stop the whole program once failing on a certain item. I just log the detailed message and go on. Or if I found a user doesn’t have enough permission for that endpoint, I throw an exception so it called by the top-level middleware. It does know how to turn in into a proper HTTP response.

    I know this is just an extended version of the GOTO operator. It looks completely imperative but I don’t care. This is a business problem, not a Haskell tutorial.

    Monads are built upon strict types

    In fact, I don’t see any reason for using monads with a language of dynamic typing system. Don’t see at all. In Clojure, we’ve got nice collections for storing either data or a nil value. Since nil is treated as an empty collection and we mostly process collections in Clojure, there is no reason to worry about whether it was a map or just nil.

    When I doubt if a value I’ve got might be nil, I just wrap the top-level form with (when value ...) which prevents me from dealing with nil. In addition, it returns nil and thus is compatible with threading macros as well.

    The very need for monads comes when you’ve got an honest typing system. An honest system is such a one that doesn’t allow to pass empty values (nil, NULL, None, etc) for an arbitrary object like one does in Java. When you are out of this trick, you’ve got to compose a complex type with a bunch of special operations upon it.

    A good example might a language with a strict typing system and algebraic types, say Scala. They haven’t got a Nil type at all. You cannot just pass an dummy value instead of a DateTime parameter. Instead, there is an Option<T> type which is a composition of either an instance of <T> class or a None value. This is only because of their type system’s limitations.

    But this is not our case! In Clojure, we are not suffering from such things. It’s much easier to check the value for its completeness with the standard if form rather than wrapping it into a monad. You overcomplicate things, and that’s the problem.

    By the way, talking about complexity. In Clojure, we don’t like complex things, we’d rather take simple ones. The entire language is about simplicity, you know. You either have got some data represented with a map or nil. That is simple. That is something you can always check within REPL out from your editor. Instead, a monad is a wrapper what obscures the original value and forces me to recover it with special macro. That’s too complex.

    Leave other languages alone

    That situation with monads in Clojure reminds me something from Python. Since it has map and reduce functions as well as flexible syntax, one believes it’s possible to program with Python in a functional way. The Internet is full of tutorials about higher order functions, functors and even monads. My shame, I used to write my own “functional” library for Python with all that stuff. It was an mess stiched from chunks of Scala and Clojure. I was really proud of it being sure this is really a great stuff. So do other authors, I suppose.

    One minor detail is, nobody uses those “functional” libraries. I’ve seen a lot of Python code before switching to Clojure. Let me assure you, a functional way in Python is a myth. There is no a chance to deliver a Django project in functional terms. Put map and reduce here and there, it won’t affect the whole picture. After all, the very language is completely imperative so you end up with changing objects through their lifetime. This is not because Python sucks, no. I love it. It’s just a matter of different design.

    Clojure also has got other design. It doesn’t know anything about monads. Talking in a more broad way, the idea of fetching foreign ideas from other languages doesn’t work. If a language is entirely imperative, functional way won’t apply here. When it has got dynamic types, the idea of adding strict type checks manually neither applies. Otherwise, you get something that we call Chimera. A strange mix of foreign elements that do not match each other. This is subject to break.

    What would you do with the team?

    One other note is, think for a while about not yourself but the whole team. Look, not everyone is as smart as you. We know you’ve been drilling Haskell by nights but know what? Nobody cares. You’ve been hired to solve business problems, not to tickle your arrogance.

    With monads, we’ve got to teach the team first. Some of my friends are really great developers yet they know nothing about monads. I don’t see any reason to violate their brains. For what? To force them to know monads? They are already capable of solving any possible business problem. Live them alone.

    I’m not against one-man-band use cases when you are the only one person responsible for everything. Use monads, monoids, do what you want. Yet it’s still an amateur way. You won’t go far as a single developer.

    Wrapping up

    Using monads is fine when you’ve got a language which is monad-friendly. They should be a part of the language’s design. Haskell or Scala would be a great choice for that.

    Railway programming looks fine right until you put that gizmo into a real project. Dull exceptions would be enough.

    Don’t borrow too much from other languages. What has been in Haskell should be left behind. It’s Clojure time! Shifting your mind between paradigms is really fun. But not sticking around the only “truthful” way!

  • Сложный выбор

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

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

    Или заморочиться, провести исследование, прочитать книгу? Но менеджер не готов выделить часы, руководство давит. Мы должны двигаться, несется со всех сторон.

    Поработать на выходных? Полно семейных дел, а два часа ничего не решат.

    С опытом приходит понимание: позади этого выбора стоит другой, более важный выбор. Как я реагирую на проблемы? Как быть, когда что-то идет не так? И не только в работе, но и в жизни?

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

    На мой взгляд, хороший разработчик ценит качество продукта, который создает. Я заметил: пока проект в тонусе, с ним приятно работать. Даже сложные задачи приносят удовольствие, если код написан чисто и с пониманием. Модули и функции сгруппированы удобно. В сложных местах комментарии и док-стринги.

    И наоборот: как только проект поплыл, любая его доработка вызывает сперва раздражение, потом злобу и равнодушие. Поплыл, значит – потерял форму, курс, наполнился нелепыми решениями.

    Пользователи слышат наплевательское отношение к коду. Может показаться, что сопли на бекенде спрятаны за интерфейсом, но это не так. Кривое поведение нет-нет, но прорвется сквозь щели. Пользователю покажут идиотскую ошибку, пришлют “[Object object]” в смс, оборвут сессию в важный момент.

    От поспешного решения больше проблем, чем пользы. Да, какую-то дырку вы заткнули. Это прекрасно смотрится в отчетности. Повышает репутацию в команде: выручил, спас проект. Но это только видимая часть.

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

    1) Это ухудшает код, а плохой код значит плохой продукт. Код – это материал разработчика. За буквами на экране стоит его архитектура, ментальная модель. Ее нельзя ломать. Код подобен башне из кубиков. По мере роста она становится нестабильной. Башня не монолит, а набор блоков. Даже если класть кубики с хирургической точностью, она все равно упадет. Вопрос в том, успеет ли она подняться на нужную высоту. Нельзя вносить помехи в и без того хрупкую сущность.

    2) Вы учите плохому новичков. К вам приходят молодые ребята, они чисты и впитывают все, что видят в проекте. Нельзя поощрять плохие практики, это дурно и с практической, и моральной стороны. Новички утащат костыли в соседний проект, потом в другой отдел. Плохая практика приживется в компании. Со временем она укрепится чужим авторитетом. На вопрос “почему так?” вам ответят “так писал сам Василий”. С полной уверенностью, что это исчерпывающий ответ.

    3) Вы заметаете проблемы под ковер. Грубое решение все равно придется исправлять. Часто об этом не ставят в известность менеджеров и старших разработчиков. Иногда якобы по уважительной причине – они были в отпуске или болели. А выпиливать костыль еще труднее, чем добавить, поэтому легче махнуть рукой.

    4) Замедление проекта. Проблему легче решить, когда в голове полный контекст о ней. Будет трудно вернуться к багу, который мигнул год назад. Разработчик, который знал все о нем, ушел. Комментарии в задаче скудные, воспроизвести не получается. Теперь, чтобы вновь наполнить голову контекстом, потребуется больше времени, чем когда проблема стояла в полный рост. Но никто не хочет этого делать. Задачу закрывают. Может, только каждый тысячный пользователь ловит этот баг, но им лень писать разработчикам. Сигнал не доходит до команды, всем наплевать.

    5) Обман самого себя. Почему-то считают, что сейчас времени нет, но потом будет обязательно. Это доводит меня до белого каления. Почему вы решили, что потом время будет? Откуда оно возьмется?

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

    6) Менеджмент не позволит. Если в проекте хоть как-то считают часы, то починить последствия вам не дадут. Проектному менеджеру платят за нововведения и продвижение продукта, но никогда — за оптимизации. Менеджер не лазит в код, он оценивает глазами и метриками. Если бага не видно, значит, его нет. И плевать, что разработчик патчит классы в рантайме.

    Опытный менеджер не выделит часы на технические доработки. Он будет тянуть до последнего. В следующем полугодии будет вагон времени на доработки, честно-честно. Нет, сразу после Нового года. Нет, после майских. Нет, в конце лета. Ребята, релиз на носу, какие доработки?

    Потом означает никогда.

    Эта проблема справедлива даже для Гугла. Недавно они обновили почту, и по всему миру люди взвыли от тормозов. На что сотрудники Гугла, бывшие и анонимные, ответили. В компании не поощряется оптимизация кода, который уже работает. На результаты такой работы не смотрят при повышении. Там считают фичи, а не число запросов на сервер. Вот и объяснение тому, что почта тормозит.

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

    Я вижу две стратегии: краткосрочную и долгосрочную.

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

    Цель краткосрочной стратегии в том, чтобы найти наименее болезненное решение. Акцент на том, что такое решение будет легче всего исправить. Мы оставляем задел на то, чтобы с наименьшими проблемами выкинуть этот код. Он должен быть написан с пониманием, его удалят. А не с мантрой “я же писал в два ночи, страдал, не трожьте, сволочи!!1”.

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

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

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

    Когда мне срочно нужна помощь, я пишу вопрос в черновике. Добавляю ссылки, куски кода, стараюсь предупредить очевидные вещи. Например, эту штуку я сделал именно так, потому что. Или этот метод не подошел из-за бага. Это здорово экономит время тех, кто отвечает. Обсуждение не размазывается по второстепенным темам.

    Потом я раскидываю вопрос по нескольким чатам: рабочий, нерабочий, профильный канал в Телеграме, Слака. На грамотно составленный вопрос отвечают, как правило, за 5-10 минут.

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

    Это была краткосрочная стратегия. Ее недостаток в том, что решение все же может оказаться недостаточно хорошим. Как мы помним, слабые решения — лишний груз в проекте. Это тот случай, когда остается признать – мы оказались бессильны перед задачей. Поможет долгосрочная стратегия.

    Долгосрочная состоит в том, чтобы научиться делать и быстро, и качественно одновременно. Это совершенно другая планка. Если краткосрочная стратегия обусловлена соглашениями в команде, то долгосрочная – это скорее внутреннее. Это про личный рост и путь.

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

    В школе это называется работа над ошибками. Делайте ее хотя бы мысленно.

    Не позволяйте себе больше одного костыля на проблему. Это должно стать мантрой. Если вы встретили проблему в первый раз, решить ее костылем не так уж постыдно. Может быть, все будет не так плохо.

    Но во второй раз пихать костыль нельзя. Долгосрочная стратегия о том, чтобы не прощать костылей. Его можно ставить только один раз. Лепить его повторно в соседний модуль, копировать по проектам — недостойное поведение.

    На верхнем уровне вырабатывается нетерпимость к плохой работе. Стратегии становятся неважны. Просто плохая работа не принимается ни под каким видом. Неважно: мало ли времени, зол ли заказчик или что-то другое. Мы так не работаем, точка. Давайте что-то менять: точнее планировать, обучать сотрудников, проводить семинары с разбором ошибок, да что угодно. Но никогда – гнать халтуру, обещая исправить ее потом.

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

    Я хочу, чтобы в следующий раз вы, вставляя костыль в код, сначала подумали. Действительно ли я решаю проблему? Какие будут последствия и кто их решит? И когда?

    Что бы сделал более опытный разработчик? Может быть, трагедии не будет, если потратить день и сделать все по уму?

    Хотя бы один такой вопрос. Тогда статья написана не зря.

Страница 33 из 75