Мы видим их издалека, а менеджерам это удаётся не всегда.
Допустим, вы находитесь в команде разработчиков, и один из сотрудников плохо выполняет свою работу, а вы ничего не можете с этим сделать.
Было время, когда любой человек в IT, будь то стажёр отдела тестирования или директор отдела разработок, хоть что-нибудь да понимал в программировании. Эти времена давно прошли, и теперь среди нас есть так называемые «специалисты» по методологии и менеджеры, не написавшие в своей жизни ни единой строчки кода, но при этом воспринимающие любую жалобу о чужой работе как ссору или личный конфликт.
Если я говорю, что один из членов команды делает свою работу некачественно (даже если я вежливо объясняюсь и рассказываю технические особенности проекта), то такие менеджеры слышат в моих словах лишь неприязнь и указывают на «сплочённость команды», намекая, что именно я проблемный сотрудник.
Внешние факторы
Ещё пару недель назад я работал удаленно на одну компанию в Англии. Один из членов команды, которого я буду называть L, не только делал свою работу ужасно (об этом ниже), но и разговаривал громче остальных на ежедневных созвонах в Zoom, даже не заморачиваясь над своим английским произношением. Он постоянно включал навязчивую демонстрацию экрана, на которой не было ничего интересного: он просто водил мышкой по экрану.
Он был как робот. На любое предложение у него была одинаковая реакция. Его очередь говорить? “Давайте я включу демонстрацию экрана”. Вылезло сообщение об ошибке? И он тут же сразу делает скриншот полного рабочего стола, на котором практически невозможно разглядеть эту ошибку. Нужно прояснить какое-нибудь ключевое слово в коде? Опять скриншот.
Со временем я стал бояться звонков, потому что от его резкого и громкого голоса у меня буквально болела голова. В то время как другие люди из команды уже отточили свой английский достаточно хорошо, чтобы быть понятыми, L всегда коверкал слова настолько сильно, что даже начинаешь понимать, почему так много компаний переводят свои команды на аутсорс из его страны куда-нибудь на Филиппины.
P.S. Многие называют меня ксенофобом за то, что я упоминаю акцент нашего L. Я думаю, не многие из таких людей на самом деле сталкивались с нетерпимостью к акцентам.
Произношение L было таким же, как и его работа, то есть едва ли лучше, чем ничего. Он был очень громким, а голос у него был такой, как будто кто-то дробит камни. Я был единственным носителем английского языка в команде разработчиков, при этом все остальные всегда говорили с умеренной громкостью и произносили слова так, чтобы их было легко понять, однако он был неисправим. Я уже привык к иностранным акцентам, но его речь казалась ещё одним подтверждением его посредственности.
Он не реагировал на общение в команде и вносил изменения в API, никого о них не предупреждая. Поскольку у нас не было разборов кода (хотя я изо всех сил старался начать их), то мы замечали эти внезапные изменения, только когда что-то ломалось.
Хуже всего было то, что L, казалось, ментально перезагружался каждые несколько минут. В этой компании были неправильно настроены git-ветки: две ветки master в одном репозитории, одна ветка для фронтенда и одна для бэкенда. Мои наработки по криптографии находились в ответвлении от ветки master в разделе фронтенда. Мы все вместе обсуждали ветки на протяжении 10 минут, и было очевидно, что я работаю в разделе “фронтенд-крипто”, ведь мы упоминали это много раз. И вот внезапно L спрашивает меня: “А в какой ветке ты работаешь?”
Такого рода ситуации случались постоянно, и менеджеры терпеливо объясняли ему то, до чего мог бы додуматься любой ребёнок. Они могли бы догадаться, что он даже не старается запомнить, но, по какой-то причине, проблемой для них было только моё недовольство по поводу того, что для него всё приходится объяснять снова и снова.
Плохой код
Обычно я работаю с семейством языков C, в веб-разработке я пишу на C#, а также учил JavaScript, Python и Django. В конечном итоге я почти всегда работал на JavaScript на фронтенде. Зачастую я выступал бэкенд-разработчиком, но в этом проекте всю бэкенд-работу выполнял L.
Он делал много работы, и вся она была низкопробной. В дополнение к нечитаемому коду, он также прилагал минимальные усилия во всем, и это сходило ему с рук.
Я доделываю свою работу
Мне требовался новый API, который бы возвращал две или более строки получателей, которые могли как быть, так и не быть в базе данных. Я не знал Django достаточно хорошо, чтобы идеально реализовать такую задумку, потому что не знал, где кончается Python и где начинается Django, однако я всё же прописал всю логику приложения и все коды состояния.
Допустим, я захотел использовать это API в поисках ключей шифрования для 10 человек. Вот пример найденного номера и коды состояния HTTP в моём фрагменте на Django:
Номер код состояния HTTP
10 200 (успешно)
1-9 206 (частично завершено)
0 204 (данные не найдены)
server exception 500 (исключение)
Если в ответе сервера будет меньше строк, чем запрошенное число, то функция возвращает массив не найденных идентификаторов.
Я переслал свой код L, чтобы он лишь поправил его синтаксис, а не переписал его, и вот что он сделал:
Номер код состояния HTTP
10 200 (успешно)
1-9 200 (ошибка)
0 200 (ошибка)
server exception 500 (исключение)
Так что даже если ни одной строки не было возвращено функцией, то, согласно его коду, это бы считалось успешным выполнением функции. Также он удалил мой массив не найденных строк, так что клиенту пришлось бы вручную вычислять возвращённые данные, сравнивать их со сделанным запросом и определять, какой из них не выдаётся в ответе функции. Да, ещё он спутал исключение сервера, которое возвращало ошибку 400, что было совершенно неверно.
Этот парень должен был быть экспертом по бэкенду и разбираться в кодах ошибок. И хотя я не знаю абсолютно все из них, но даже я могу назвать больше десяти самых распространённых. И даже имея логику приложения и предполагаемые коды состояния прямо перед носом, он всё стёр и сделал по-своему.
Справедливости ради стоит отметить, что существует несколько подходов к тому, как обрабатывать промежуточные состояния прохождения API по серверу. Я крайне редко встречаю какие-либо ошибки 2ХХ, кроме 200. Ошибки 200 и 500 — это единственное, что вообще возвращают разработчики в своих функциях. Многие из них знают три-четыре кода состояния. L знал лишь два, и один из них он знал неправильно.
Было бы слишком снисходительно подумать, что у L есть свой подход, не похожий на мой. Он мог бы предположить, что раз я использую более четырёх кодов состояния, то это значит, что они всё-таки нужны. Однако из нескольких месяцев работы с них я уже знал, что он просто взял и скопировал одну и ту же строку кода, вероятно взятую со StackOverflow, для каждого состояния. Он оставил мою логику отсеивания ошибок для случаев 0, 1–9 и 10, но к каждой из них вставил одну и ту же строку.
В любом случае API — это транзакция, и если он изменил его поведение, то должен был сообщить остальным об этом, поскольку мы ожидали этих более подробных кодов состояния. Он не только не потрудился сделать этого, но ещё и не ответил мне, когда я спросил его об этом. Так в команде не работают. И поскольку в этом проекте не было контроля качества, то, скорее всего, именно клиенты первыми сталкивались с ошибками в логике приложения.
Как на это реагировали менеджеры
Я был в ярости. Я всё сделал правильно, за исключением синтаксиса на Django, который L смог бы исправить меньше чем за минуту, но вместо этого он переписал всё с сильно изменённой логикой. И конечно, его код выглядел так, будто он головой ударил по клавиатуре.
Я пытался узнать у L, зачем он сделал все те изменения, но когда он как обычно проигнорировал меня, я позвал менеджеров на групповой звонок. Я показал им то, о чём писал выше. В ответ на это они лишь вздохнули и сказали, что поговорят с L. Я не думаю, что они правда сделали это, потому что спустя две недели всё осталось неизменным.
И они всё же оплатили работу этому человеку. А если они не поговорили с L, значит, скорее всего, решили, что я привношу конфликты в команду, хоть никогда мне об этом и не говорили.
Это был последний раздел моей работы, и все части кода действовали исправно, за исключением этого испорченного API. С меня было достаточно. У меня три языка за плечами с опытом работы в действительно классной криптографической реализации.
Я больше не утруждал себя снова говорить с L. Какой в этом смысл? Он проделал как минимум паршивую работу, и, согласно его рабочим стандартам, это была норма. В нашем предыдущем обсуждении дизайна он не привнёс никаких идей. Я бы мог наставлять его, но за месяцы работы с ним я уже знал, что он бы проигнорировал меня и продолжил бы делать свою работу так, как он привык: небрежно, криво и неразборчиво.
Менеджеры, не знающие кода
Как и многие другие, кто говорит, что навыки работы с людьми важнее, чем умение программировать, так и менеджеры нашего проекта были больше заинтересованы в том, чтобы поддерживать дружескую атмосферу в команде, чем в создании надёжного продукта. Так как это было ориентированное на безопасность приложение, для нас было более важно сделать работу по наиболее строгим стандартам, но менеджеры разрешили L небрежно переписать свой код и остаться в команде.
Их отношение к моей жалобе, вероятно, выражалось в том, что они думали, будто между мной и L есть некоторые “разногласия”. Я прекрасно ладил со всеми и пытался скрывать своё недовольство L и его загадочными выходками и ужасным кодом.
Вся эта ситуация напоминает то, что происходит, когда процесс разработки воспринимают как социальную деятельность. Это никакое не программирование. Но если бы я был ведущим разработчиком, то L бы уже искал себе другую работу.
Рабочая этика разработки ПО состоит из двух полюсов:
- Вы делаете работу как можно лучше и забываете про сроки.
- Вы делаете как можно меньше, а вычёркивание задач из списка дел — ваш единственный приоритет.
L и я были на разных полюсах этого процесса.
Читайте также:
- Лучшие приёмы HR от Google
- Почему я перешёл на Linux после 10 лет работы на Windows
- Искусство обращаться за помощью к коллегам-программистам
Читайте нас в Telegram, VK и Яндекс.Дзен
Перевод статьи Chris Fox: Working With a Really Terrible Developer