Я работаю iOS разработчиком более шести лет. Мне довелось работать в нескольких различных компаниях и командах. Я работал как в outsource так и в outstaff, довелось даже поучаствовать в startup. И вот спустя несколько лет коммерческой разработки, а также пару-тройку лет программирования в университете, я стал выделять некоторые принципы или правила качественного подхода к разработке приложений. Сначала это были советы моему другу. Давая ему советы, я подумал, что мне не хватало подобных советов, когда я только начинал свой путь разработчика. Та что там говорить, некоторые моменты я понял для себя сравнительно недавно, а некоторые уже на новом месте работы. И вот родилась идея составить список советов, которыми мне бы хотелось поделиться с самим собой пять-шесть лет назад. Я уверен, что ещё через пять лет у меня будет что сказать себе сегодняшнему. Но это оставим пожалуй на будущее.
Твой код плохой
И первое, чтобы мне хотелось сказать себе прежнему, так это: “Твой код плохой!”. В простонародье ”говнокод”. А у зарубежных коллег по девелоперскому цеху «monkey code”.
Нет это не то что вы подумали. Я не хочу подчеркнуть, что раньше я был плохим кодером, а сейчас мой код идеальный. Я хочу перефразировать это послание и передать три ключевых момента в смысле этого совета.
“Твой код был есть и будет плохим!”
Момент первый: нет идеального кода, никто не закладывает идеальную архитектуру и нет такого кода, в котором не было бы багов. Думаю многие ловили себя на мысли, что не смогут разобраться в новой библиотеки или в новой технологии. Либо же некоторые из нас впадали в крайность в попытках написать фичу идеально, следуя всем принципам OOP, SOLID. Что в свою очередь приводило к большим временным затратам, а иногда заводила в тупик. Иногда в попытках написать идеальный код, рождались чудовища, которые несли в себе полный список паттернов, которые знает разработчик, А может даже ещё больше.
Своей фразой я бы хотел донести идею, что не стоит в первую очередь переживать, нервничать за качество своего кода. Предугадать всего невозможно. И лучше просто расслабиться, написать проще и как знаешь, нежели понапрасну страдать и переживать. С опытом решения придут сами собой. Иногда нужно “наговнокодить”, столкнутся с проблемами, которые вызовет этот говнокод и понять раз и навсегда, что так делать лучше не надо.
Момент второй, о чем я уже упоминал ранее, так это то, что всего предугадать практически невозможно. Да, С опытом приходит понимание того, что ты делаешь И можно предугадать пути развития проекта. Но это приходит с опытом. А если опыта не хватает, то не стоит пытаться сделать код универсальный. Бывают нередкие случаи, когда твою фичу, которую ты долго и так тщательно сначала продумывал А затем писал, просто выкидываются с приложения. Также нередки случаи, когда приложения меняются только потому, что у заказчиком в голове это всё представлялось по-другому. И вот после долгих часов кропотливого переноса интерфейса с дизайна в код, вдруг появляется 100500 правок. Это только начало так как после первого переделывание будут приходить все новые и новые правки. И в случае, когда разработчику не хватает опыта, этот процесс может занимать не только много времени но и приносить не самые приятные ощущения, которые откладываются неприятными мыслями где-то потайных уголках разума, превращая процесс разработки с весёлого занятия в адскую боль. Поэтому берегите свои нервы и не годитесь за идеалом. Иногда можно и немного поговнокодить.
Третий момент: это опять-таки чисто психологический момент, а именно критика со стороны других разработчиков. Как все знают, все отечественные разработчики считают любой чужой код — говнокодом. Даже если ему показать его собственный код, который он не узнает, то он с большой вероятностью наречет его говнокодом. Нередко такая вот критика сопутствуется моральным удовлетворением самого критика. Как отмечают опытные разработчики, то больше всего говнокодом называют чужой код именно те, кто в свое время наговнокодил с лихвой. И чем громче кто-то кричит “говнокод”, тем больше своих “лепех” он оставил на своем пути.
К тому же любой дев, которые вспомнить себя молодым, обязательно признает, что он наговнокодил на славу.
Поэтому советую использовать выражение “Твой код был есть и будет говнокодом”, как щит от не всегда конструктивной критики. Хочу также отметить, что твой код всегда будет говнокодом потому что развитие не стоит на месте. С каждым годом качество твоего кода только улучшается. Так что текущий код со временем все равно превратится в говнокод.
Разделяй и властвуй
Не хочу чтобы показалось, что я советую только говнокодить, поэтому начну давать советы по избежанию того самого плохого кода. И начать хотелось бы с принципом, которые я выделил сам для себя. Нет, это не наследования или полиморфизм, и не один из принципов SOLID. Этот принцип я называю ”Разделяй и властвуй”.
Да, есть такое понятие как декомпозиция.
Декомпозиция — разделение целого на части. Также декомпозиция — это научный метод, использующий структуру задачи и позволяющий заменить решение одной большой задачи решением серии меньших задач, пусть и взаимосвязанных, но более простых.
Как гласит Википедия. Но это только часть того, что я вкладываю в смысл моего принципа. Однозначно да, нужно делить проект и задачи на более мелкие части. Но я имею в виду концептуальный подход к разделению логических групп в проекте.
И первое чтобы я отнес к этому принципу, так это разделение пользовательского интерфейса И бизнес логики приложения. Казалось бы я сейчас прям капитан очевидность. Но! На практике эти границы зачастую размываются и выходит так что ViewController или Activity содержат в себе частичку бизнес логики.
Думаю, простым и понятным будет пример экрана “Login”. Вот начинает разработчик внедрять архитектуру MVC. Вроде есть отдельно View, вроде и Controller с Model также добавляет, как и полагается. Но в какой-то момент задумываются: “А зачем мне добавлять несколько классов для экрана с одной единственной кнопкой?” и в этот момент я настойчиво рекомендую отказываться от подобных порочных мыслей и строго придерживаться принципа “Разделяй и властвуй” для разделения UI и бизнес логики. И даже если архитектура требует добавить класс ViewModel, в котором будет одна две строчки кода, следует так и сделать. Потому что часто бывают случаи, когда экран, в котором была изначально одна кнопка, со временем разрастаются до немыслимых сложностей. Если заранее следовать разделению логических компонентов, то это в разы облегчит жизнь в дальнейшем.
Особенно почувствовать суть строгого разделения UI и логики, можно в тех случаях, когда приходится переносить экраны с одного проекта в другой. Либо же в ситуации, когда при разных условиях применяются разные алгоритмы в бизнес логике. Например, разделив экран авторизации на компоненты мы можем в будущем заменить один из компонентов не затронув другой. Мы можем либо заменить View, либо Model с новым способам авторизации для тех же данных.
Не стоит ограничивать принцип “разделяй и властвуй” только этими двумя слоями. К строгому разделению Я бы ещё добавил разделения экранов и логики навигации для мобильных приложений. Что я под этим имею в виду?
Моя практика подтолкнула меня к тому, что облегчить код для конкретного экрана можно тем, что вынести отдельно логику навигации. Экран, а конкретно View, для iOS это UIViewController, а иногда и UIView, а для Android Activity, либо же Fragment, не должны заниматься функцией для отображения самому себя, а также перехода на другие экрана. Каждый из этих классов должны заботиться только о том, что происходит на конкретном экране, а вернее только за отрисовку конкретного экрана и взаимодействие с классом бизнес логики (Presenter, ViewModel и другие).
Это только два из множества примеров, где нужно принципиально следовать разделению. Следование этому принципу в разы облегчит дальнейшую работу с проектом. Даже если в любом из отдельных компонентов заведется говнокод.
Единый стиль
Плавно исходя из предыдущего совета, хочу перейти к следующему, а именно строгое соблюдение единого стиля в проекте.
Что я под этим подразумевают?
Начну с того, что ключевое слово здесь строго, от слова совсем. Изначально подбираем единый подход для организации проекта, для файл менеджмента, для стиля кода и так далее. Это в разы улучшит общий вид проекта и намного облегчить навигацию по проекту, поиск по коду, ускорит процесс ознакомления нового разработчика на проекте. Думаю не стоит напоминать, что через некоторое время мы сами можем стать этим новым человеком со своим старым кодом.
Выбор архитектуры и следование ей
Опять-таки исходя из предыдущего совета плавно переходим к следующему, выбор архитектуры. И основная мысль, которую я хочу донести, это это не рассказать о наилучших архитектурах или сказать, что нужно выбрать эту, а не другую. Нет! Начну с того, что нет идеальной архитектуры, которая бы полностью покрывало все возможные кейсы в проекте. Я когда-то услышал такие слова:» если бы была идеальная архитектура, то нас, разработчиков, уволили бы за ненадобностью и заменили бы на скрипты, которые генерирование идеальную архитектуру".
Главным моментом, я считаю, является не выбор наилучший архитектуры, а опять-таки строгое следование той архитектуре, которую уже выбрали и начали применять. Будь то хоть VIPER, REDUX, MVP или MVC. Есть конечно же плюсы и минусы в каждый из вышеперечисленных архитектурах. Со временем появляются все новые и новые подходы к проектированию архитектуры проекта.
Более конкретно скажу по поводу моей идеи. Если уже начали использовать VIPER, то строго следуйте его принципам. Даже если кажется, что для экрана с одной кнопкой уж слишком много нужно создавать файлов с единицами строк кода, то не при каких обстоятельствах не обходите эти правила. Потому что, вот в такие вот моменты и рождается говнокод, который потом как снежный ком все наращивается и наращивается.
Советую перед началом разработки нового проекта ознакомиться с самыми популярными архитектурными и выбрать либо ту, которая понравиться, либо самую популярную. Настоятельно рекомендую выбрать второй вариант, а именно начать с самой популярной архитектуры, т.к. можно будет легко найти ответы на многие вопросы. При выборе архитектуры особое внимание нужно уделить минусам этой архитектуры и то в каких случаях её рекомендуют использовать.
Например, если небольшой проект, на котором один два разработчика, то не стоит брать VIPER из-за того, что это довольно громоздкая архитектура, которая очень хорошо себя проявляют на больших проектах и в больших командах. Чтобы не было случаев, когда кода для создания VIPER больше в разы чем кода самой бизнес логики.
Лично я сейчас предпочитаю архитектуру MVVM+Router. Она хорошо подходит на небольшом проекте, где я один разработчик.
Итог: главное, не какую архитектуру выбрали, а то насколько точно вы ей следуете.
Также хочу добавить, если проект не разрабатывается с нуля, то в первую очередь нужно ознакомиться с текущей архитектурой и общим стилем проекта, и начать следовать ему. Не стоит вырываться с криками, что здесь говнокод (возвращаясь к первому совету) и начать переделывать все. Исключение может быть, полная анархия на проекте либо отсутствие общей стилистике.
Паузы на рефакторинг
И в заключения хочу сказать, что хорошим подходом будет делать паузы на рефакторинг. Рефакторинг очень важная часть качественной разработки приложений. Да, мы не пишем код идеальный сразу, но и оставлять всё как есть, тоже не есть хорошо. Часто бывает, что исходная реализация не имеет возможности масштабирования, кода нужно вносить новые фичи. Ведь практически невозможно предугадать все возможные изменения в будущих версиях проекта. Также ни одна архитектура не гарантирует 100% покрытие всех случаев. Поэтому важно вносить изменения в уже имеющийся код с целью адаптировать его под новые фичи.
Автор: ruslanshevtsov