Pull to refresh

Comments 41

Зашел чтобы прочитать этот коммент.
>Владислав Чернов: Мы используем git rebase, мы именно его используем, потому что git revert нас не устраивает, так как мы разрабатываем каждую задачу в отдельной ветке. Если мы откатываем с помощью revert после сливания ветки релиза и ветки мастера, то разработчику придётся делать revert на revert, поэтому мы используем git rebase. Мы моментально откатываемся, соответственно, собираем новую сборку и выкладываемся на стейджинг.

Признайте честно, что просто не осилили git revert и cherry-pick. В результате, например, разработчикам под страхом страшной смерти нельзя мержится от ветки, к которой ещё могут запустить git rebase.
А зачем разработчику мержить себе в ветку релиз, если он через 4 часа всё равно будет в мастере? Если есть какая-то зависимость между задачами, то можно замержить отдельную задачу, это намного безопаснее.
Например, разработчик может сам разрешать конфликты, поскольку лучше понимает функционал, чем релиз-инженер. Вообще же, замена функционала итп часто обратно несовместима, и на дев-платформах это легко разрешать банальным мержем с мастером/релизом.

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

Кстати, привет 2 хейтерам из Баду.
Все конфликты решают разработчики, релиз-инженер этим не занимается. Вот, как сейчас. Вы задаёте конфликтные вопросы, а отвечают на них разработчики =)
Эгегей — Хейтеры из Баду, friendly fire, свои! не надо минусить мои комменты! Или тут не только из Баду хейтеры таки? =))
Про мастер-продакшен вы правы, если мы это делаем то откатываем через revert.
Но это бывает крайне редко.
Здесь говорилось только про ветку релиза.
По поводу конфликтов у нас сделано просто благодаря той самой автоматизации. если автомерж не смог залить какую-то ветку в билд, то задаче выставляется специальный флаг в Jira чтобы предотвратить дальнейшие попытки автомержа и с AIDA переводится обратно на разработчика с комментарием что в такой-то билд её не удалось замержить.
Логично. Проблема в том, что после этого разработчик мог бы просто смержить в свою ветку мастер/релиз и таким образом легко разрешить конфликт. А так, придётся угадывать ветку, с которой произошёл конфликт, мержиться с ней, и всё равно иметь проблемы в случае отката ребейзом любой из этих веток.
А можете более развернуто описать Ваш workflow? И как откатываете изменения.
Да, будет отдельная статья про то как мы откатываем изменения из ветки релиза и небольшое описание нашего flow.
Про флоу мы уже писали в статьях тут и тут. Но отдельной статьи, посвященной именно флоу, у нас еще не было. Обязательно напишем. Так же, как Влад уже написал, готовится отдельная статья про автоматизированные откаты задач из ветки релиза.
UFO just landed and posted this here
Спасибо. Но меня интересовал именно git workflow (возможно, мне стоило уточнить это). У нас прижился такой подход:

1. ветка от мастера
2. работа
3. подливаем мастер в ветку
4. мерджим ветку в мастер

ИМХО, он наиболее демократичен и гибок.

При возникновении проблем, в мастере делается реверт. Но иногда возникают ситуации, когда реверт на реверт на реверт и уже сам путаешься.

Хотелось узнать хотя бы на пальцах про откат ребейзом и общие принципы ветвления, принятые у Вас.
UFO just landed and posted this here
1) Ветка от мастера для задачи — работа — Code review — тестирование
2) Ветка релиза от мастера
3) Автомерж веток готовых и протестированных задач в ветку релиза — интеграционное тестирование и staging
4) Нашли багу, откатываем смерженный коммит задачи из релиза c помощью rebase — сборка — повторная проверка на staging
5) Едем на продакшен — проверяем опционально
6) Если все хорошо — сливаем релиз в мастер
7) Все плохо(исключительный случай:)) перекидываем линк на предыдущий релиз.

Два релиза в день, по времени, автомерж тасок останавливается за 2 часа до выкладки на продакшен очередного релиза.

Если кратко:)
Если не сложно, ответьте на несколько простых вопросов:

1. Если представить, что у вас есть две группы разработки, серверная и клиентская, плюс группа системных администраторов, то как вы выкатываетесь?

2. Прошу пояснить что в вашем понимании 100 тасков в день.

3. Как тестировщики успевают протестировать весь проект всего за одинь день?

4. Какие критерии вы используете оценки что релиз «удался»

5. Кто может ставить таски на разработчиков?

6. Есть ли у вас ручное тестирование интерфейсов. Если есть, то какое у них воркфоу?

Подключусь к вопросам

7. Если Stage работает с продакшен базой, как происходит тестирование при изменении схемы(мажор фича, к примеру)? Используются ли инструменты для миграций?

8. Я так понял ветвитесь только в один уровень, а если нужно работать группой разработчиков над одной фичей и каждый будет ветвится от этой фича-ветки?

9. Были ли случаи, когда на продакшен ушла очередная фича, но через несколько релизов оказалось, что её нужно откатить. Как происходит этот процес?
7. С базой у нас все просто если нужно что то добавить мы просто заранее делаем нужный альтер, и старый код работает как работал, потом выезжает новый код начинает работать с тем что мы добавили, проверяем все ли хорошо (при этом это уже проверялось на devel окружении), дальше при надобности удаляем ненужное. Миграция — боюсь ошибиться, но нет.
8. Нет каждый будет создавать свою из мастера (декомпозиция задач смотрите выше). Можно вести разработку в одной ветке, либо при надобности смержить их. Смерженные таски отслеживаются на уровне Git и Jira и задача если зависит от другой по коду не уедет в релиз автоматически.
9. Если вы про откат фичи с багом, то нет так как слишком много этапов тестирования и много тестов, так что все баги ловятся на этапе релиза. Бывает реверт из мастера раз в полгода, но это отлавливалось в тот же день. Если вы про выпиливании работающий фичи, то она выключается как и включалась, после этого аккуратно выпиливается код.
с базой чуть-чуть сложнее
* если код не может работать прозрачно с новой схемой — сначала идет фикс-релиз кода (так стараемся не писать, но всяко бывает)
* альтер по-живому (если по кластеру — то шард за шардом)
* релиз, использующий новую схему
* (опционально) clean-up процедуры над базами
а вообще хотя задача и сложная чисто теоретически (100% плавного алгоритма на все случаи жизни нет), на практике организационно все разруливается довольно легко
Спасибо за вопросы
1. Не надо даже представлять, так и есть. Только вы забыли еще группу релиз инженеров. Если говорить об обновлении, то системные администраторы обновляют сервисы и происходит это в момент наименьшего трафика на сайт. Сервер обновляется два раза в день, при этом серверное API (имеется ввиду сервер-клиент) пишется так чтобы не ломались старые версии приложений(если что разработчики меня поправят) и параллельно разрабатывается клиент. Тестируем чтобы новая фича ничего не сломала, что она работает на сервере, что работает с клиентом и выкатывается на сервер. Когда выходит новая версия клиента она использует новую функциональность на сервере.
2. У нас большие фичи декомпозируются на множество мелких задач, разрабатываются и тестируются (например на тестовых пользователях) именно в такой архитектуре, притом последней уезжает таска которая включает данную большую фичу для всех пользователей. Так что это может быть совершенно разные задачи, начиная от багфиксов и заканчивая включением новой большой функциональности на продакшен.
3. Мы используем большое количество автотестов на всех этапах тестирования, и стараемся особо покрывать критичные моменты. Плюс постфактум за проектом следит отдел мониторинга у которого огромное количество различных графиков и триггеров. Ну и конечно ручное тестирование задач которые в релизе. Опционально также проверяем продакшен вручную.
4. Работают новые фичи + ничего не сломалось при выкатке= релиз удался
Если что то случилось, мы не говорим что релиз плохой, а в максимально короткие сроки либо откатываемся, либо фиксим проблемы если они не так критичны и фикс займет очень короткое количество времени.
5. Если баг то QA, сами разработчи, если фича то продукт совместно с лидами, если рефакторинг сами разработчики. Жесткой бюрократии у нас нет.
6. Я не очень понял вопрос, думаю что тестирование ответит вам гораздо лучше:) Илья?
Расскажите как вы поддерживаете консистентность данных. Если я правильно понял, то из за шардинга вы не можете использовать выстроенные в ДБ механизмы типа внешних/уникальных ключей.
Тут путаница. Уникальные ключи, конечно, есть. В шардированной схеме мы внешние ключи не используем по историческим причинам, но это можно сделать. Консистентность будет в пределах шарда, но это как раз нормально — именно это и требуется. Тем не менее, жить без нее не сильно сложнее, как показала практика. Отказ от внешних ключей для датабазника может показаться очень странным (я сам до этого сидел 3 года на оракле), но консистентность по внешним ключам действительно оказалась почти не нужной. Каскадные удаления — фактически единственное реальное удобство, которого нет. Но мы не удаляем данные, а олдскульно помечаем статусами. Удаляется все потом единообразная системой пуржинга. Вообще один-два раза в года я рассказываю об этом подробнее на семинаре в рамках девконфа, например.
Спасибо за ответ. А статья по теме «БД в Баду» не планируется?
6. Ручное тестирование есть и флоу у него ничем не отличается от описанного выше. Задачи (новые фичи, багфиксы и т.п.) приходят в QA сразу после выполнения. На этот момент задача уже прошла code-review и прогнаны автоматом юнит-тесты (в тикете в джире есть репорт об этом). Тестировщики тестят это в девелоперском окружении, если все хорошо — следующий этап это тестирование задачи в шоте. Шот — это пре-продакшен для отдельной ветки кода. Если, опять же, все хорошо, то следующий этап — тестирование билда из смерженных фич на стейджинге. Ну и все что протестировано на стейджинге, уезжает в продакшен. Все эти этапы тестирования включают как ручное, так и автоматизированное тестирование. Интеграционные тесты QA-инженеры пишут на phpUnit, с использованием Selenium WD. Ручное тестирование включает в себя как регрессионные проверки фич, для которых по тем или иным причинам еще нет селениум-тестов, так и exploratory-тестирование фич. Ну и проверка фронтенда (верстка, js и т.д.) в разных браузерах, в зависимости от популярности по статистике посещения.
А можете чуть подробнее рассказать о шотах?
Если они не изолированы друг от друга, т.е используют одинаковые подключения к базам, то, получается, они могут влиять друг на друга(общий кеш, поменялась структура данных уходящих в очередь и тд)?
В функциональных тестах какая база используется? Та же, что и в девелоперском окружении? Если да, то при постоянном запуске(100 задач * 18000 тестов) она будет забиваться различными данными. Или все же используются для этого отдельные снапшоты/фикстуры БД?
Шот это просто папка с гитом, где счекаучена ветка задачи + настройки nginx, чтобы можно было зайдя по определенным точкам входа увидеть веб-морду, апи для клиентов и т.д. Эта папка выгружается на одну из машин в боевом окружении, где и тестируется.
По другим ресурсам — базам, мемкешам, демонам — они не изолированы, вы правы. И риски о которых вы говорите тоже имеются, никуда от этого не деться. Но мы минимизируем эти риски, когда тестируем задачу до шотов — в девел окружении. Где все вышеперечисленные ресурсы отделены от продакшена.
Интеграционные селениум-тесты гоняются в двух окружениях — девелоперском и стейджинговом. Для них используется отдельный пулл объектов, не затрагивающий основных пользователей ресурса.
Для девел-окружения, где (и только где) гоняются еще и юнит-тесты и функциональные тесты, отдельных снапшотов с данными не используем. Данные после сетов тестов либо роллбечим в транзакциях (где это возможно), либо используем моки таблиц. У нас есть свои классы/механизмы для этого, мы подменяем на лету таблицы и запросы к ним в коде. Таблицы делаются темповыми (за небольшими исключениями) и сами удаляются после тестов движком БД. Для тех мест, где нельзя использовать темповые таблицы, есть оффлайновый скрипт, который пробегается и чистит такие таблицы.
Безусловно, бывают ситуации, когда тесты все же оставляют данные в девелоперских базах, но это не критично, ибо 1) используем подход «каждый тест должен сам для себя готовить данные, независимо от того, что в БД или других общих ресурсах было до него» и 2) ничто не мешает в любой момент перезалить девелоперскую БД.
Ведете ли вы общий тест-план проекта, что в него попадает и смогли ли вы автоматизировать его пополнение?
От части таким тест-планом выступает набор автотестов. Отдельно от этого ничего не ведем. Ну если не считать описание фич в confluence, которое ведется продактами и корректируется по ходу реализации.
Расскажите, пожалуйста, о базах: что используете, почему используете и какие действия предпринимаются когда нужно сделать миграцию или откатить ее.
Используем mysql, по историческим причинам (ну и вообще — отличная база, просто не нужно стрелять себе в ногу и всё). У нас кстати одна из крупнейших ферм MySQL — под 500 уже наверное нод в двух ДЦ. Миграция — это выполнение в паралелль по нескольким сотням нод какой-то операции, есть фреймворк под это дело, откатить — ну так же как и на одной базе. Вы умеете на одной базе откатить альтер, например? Я — нет. Надо снова альтерить — опять в параллель пускаем операции на нодах. Всё олдскульненько.
боже упаси. InnoDB конечно
Спасибо большое за интервью. Сам проработал много лет релиз-инженером, отлично понимаю, насколько важную работу и насколько хорошо ребята выполяют в команде.

Удач и успехов, в общем, пишите ещё.
UFO just landed and posted this here
Кстати, Сергей Авдюшкин не в этой же команде часом?
ребята, решите что-то с ресайзом фотографий.
а то глаз режет (

image
Да, согласны, мы сейчас решаем как раз этот вопрос.
Расскажите, как файлы, которые разработчик пишет на своей локальной машине, оказываются на его dev-сервере? Монтирование, синхронизация?
В данный момент наши разработчики используют каждый, кто во что горазд :).
Варианты, как минимум:

— sshfs
— SMB
— rsync «руками»
— загрузка изменений, встроенная в PHPStorm
— realsync
— моя утилита, вместо realsync, которая умеет синхронизироваться на несколько серверов (сильно альфа :))
Sign up to leave a comment.