. Сети Петри с Symfony а-ля WorkFlow компонент
Сети Петри с Symfony а-ля WorkFlow компонент

Сети Петри с Symfony а-ля WorkFlow компонент

Давайте представим некоторый проект на GitHub, куда мы хотим оформить Pull Request. Здесь нас будет интересовать только тот огромный жизненный цикл нашего пулл реквеста, который он фактически может пройти с момента рождения до самого момента его принятия и мержа в основной код проекта.

Итак, если порассуждаем, то пулл реквест может иметь следующие варицации над состояниями, которые я специально усложнил, если не знать о WorkFlow и смотреть на подобное тз:

1. Открыт 2. Находится в проверке в Travis CI, причем может попасть туда после того как были сделаны какие-то исправления или любые изменения, связанные с нашим Pull Request, ведь проверить-то надо все, не так ли? 3. Ждет Review только после того как была сделана проверка в Travis CI 3.1. Требует обновлений кода после того как была сделана проверка в Travis CI 4. Требует изменения после Review 5. Принят после Review 6. Смержен после Review 7. Отклонен после Review 8. Закрыт после того, как был отклонен после Review 9. Открыт заново после того как был закрыт, после того как был отклонен, после того как было проведено Review 10. Изменения после того как был помечен «Требует изменений», после того как было проведено Review, при этом после этого он снова должен попасть в Travis CI (пункт 2), а от Review снова может с ним случиться только те состояния, которые мы описали выше Жесть, правда?

То, что в квадратах — мы будем называть транзакциями, тем временем всё то, что находится в кругах — это те самые состояния, о которых мы ведем речь. Транзакция — это возможность перехода из определенного состояния (или нескольких состояний сразу) в другое состояние. Здесь и вступает в игру WorkFlow компонент, который будет помогать нам управлять состояниями объектов внутри нашей системы. Смысл в том, что сами состояния задает разработчик, тем самым гарантируя, что данный объект всегда будет валиден с точки зрения бизнес логики нашего приложения.

Если человеческим языком, то пулл реквест никогда не сможет быть смержен, если он не прошел заданный нами ОБЯЗАТЕЛЬНЫЙ путь до определенного момента (от проверки в тревис и ревью до его принятия и самого мержа).

Итак, давайте создадим сущность PullRequest и зададим для неё правила перехода из одних состояний в другие.

Вот как это будет выглядеть, когда ты знаешь что такое WorkFlow:

Так же как и на картинке, мы задаем определенные состояния, в которых фактически может прибывать наша сущность (framework.workflow.pull_request.places): start, coding, travis, review, merged, closed и транзакции (framework.workflow.pull_request.transactions) с описанием, при каком условии объект может попасть в это состояние: submit, update, wait_for_review, request_change, accept, reject, reopen.

А теперь снова вернемся в жизнь:

Submit — это транзакция перехода из начального состояния в состояние проверки изменений в Travis CI.

Это наше самое первое действие, здесь мы оформляем наш пулл реквест и после этого Travis CI начинает проверять наш код на валидность.

Update — транзакция перехода из состояний coding (состояние написания кода), travis (состояние проверки на Travis CI), review (Состояние, когда происходит review кода) в состояние проверки Travis. Это то действие, которое говорит системе, что нужно снова все перепроверить после каких-либо изменений в нашем pull request, т. е. в том, что готовится смержится в мастер.

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

Request_Change — транзакция перехода состояния из Review в Coding. Т.е. тот момент, когда (к примеру) команде проекта не понравилось то, как мы решили поставленную задачу и они хотят увидеть другое решение и мы вносим какие-то изменения в виде исправлений снова.

Accept — транзакция перехода состояния из Review в Merged, конечная точка, которая не имеет после себя никаких возможных транзакций. Момент, когда программистам проекта нравится наше решение и они его мержат в проект.

Reject — транзакция перехода состояния из Review в Closed.

Момент, когда программисты не посчитали нужным принимать наш pull request по каким-либо причинам.

Reopen — транзакция перехода состояния Сlosed в состояние Review.

Например когда команда программистов проекта пересмотрела наш пулл реквест и решила его пересмотреть.

Теперь давайте уже наконец-таки напишем хоть какой-нибудь код:

При этом, если абстрагироваться, то иногда бывает так, что сам объект может иметь несколько состояний одновременно. Помимо state_machine мы можем прописать нашему объекту тип workflow, что позволит одновременно иметь несколько статусов у одного объекта. Примером из жизни может послужить ваша первая публикация на хабре, которая одновременно может иметь статусы, например: «Мне нужна проверка на плагиат», «Мне нужна проверка на качество» и которая может перейти в статус «Опубликована» только после того как все эти проверки пройдены, ну это конечно при условии, что все эти процессы не автоматизированы, но мы сейчас ведем речь не об этом.

📎📎📎📎📎📎📎📎📎📎