JavaRush /Java блог /Random UA /Пишемо проект. Додаємо SpringBoot і налаштовуємо CI проце...
Roman Beekeeper
35 рівень

Пишемо проект. Додаємо SpringBoot і налаштовуємо CI процес - "Java-проект від А до Я"

Стаття з групи Random UA
Стаття із серії про створення Java-проекту (посилання на інші матеріали – наприкінці). Її мета — аналіз ключових технологій, результат — написання телеграм-бота. Вітаю вас, дорогі читачі. Як було описано у попередній частині, будемо йти за планом. Ми вже створабо проект і настав час його наповнювати кодом. Тепер все це буде додаватися окремими комітами. Все, що буде потрібно, я опишу тут. Якщо щось упущу або опишу недостатньо зрозуміло — питайте у коментарях, намагатимусь відповісти."Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 1

Пишемо JRTB-0M

У цьому питанні нам потрібно додати порожній SpringBoot каркас для майбутньої роботи. Робити ми це будемо так само, як і робабо у статті про SpringBoot + Flyway . Качаємо проект , відкриваємо його в IDEA і створюємо нову гілку під назвою JRTB-0 . Як це зробити через ідею я описував тут . Так буде зручніше для нас у майбутньому для відстеження роботи. "Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 2Ви вже знали, що тепер немає гілки master ? Тепер вона називається нейтрально - main . Тому звикаємо. Хоча, правду кажучи, ми завжди можемо перейменувати її назад у майстер. Заходимо на Spring Initializr та створюємо SpringBoot каркас для нашого бота."Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 3На даний момент наймолодша пропонована версія спринту бута - 2.3.7, беремо її. Наступні опції опишу окремо:
  • Project: Maven Project — ми вже розібрали мов тут і тут . Тому додатково описуватиму тільки те, що не розкрив у попередніх статтях. Якщо такі "білі плями" будуть, звичайно)
  • Language: Java – тут все зрозуміло. Буде бажання – можемо переписати цю справу на Kotlin. Я якраз прикупив собі книжечку Kotlin in Action, навчатимемо котел разом))
  • Spring Boot: 2.3.7 - беремо найменшу із запропонованих версій, щоб виключити будь-які проблеми. Це й так цілком сучасна версія бута.
Project Metadata:
  • Group: com.github.codegymcommunity - тут вибираємо домен, на якому хоститься наша група репозиторіїв.
  • Artifact: codegym-telegrambot – максимальний опис проекту.
  • Name: Javarush TelegramBot – тут вже повністю напишемо.
  • Description: Telegram bot для Javarush з community to community — тут вже детальніший опис проекту.
  • Package name: com.github.codegymcommunity.jrtb — тут можна використовувати абревіатуру для імені проекту. Тепер із цього пакету розпочинатиметься проект. Навіщо так багато? Щоб коли ми додавали до classpath інші проекти, вони були у різних пакетах. Кожен у своєму унікальному. Це важливо зберегти ООП принципи.
  • Packaging: Jar – це наш стандарт)
  • Java: 11 - будемо на крок попереду. Не думаю, що я використовуватиму нововведення після восьмої джави, але нехай уже буде. Їсти не просить)... це рішення підкладе нам невелику пасхалку в майбутньому)
Поки що залежностей ніяких додавати не будемо. В рамках цього завдання нам цього не потрібне. Заповнивши все це, отримаємо (ось посилання на згенерований проект): "Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 4Заповнивши, натискаємо GENERATE і додаємо в наш проект всі начинки в архіві. "Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 5Додаємо файли до проекту. У результаті ми маємо додаток. Щоб перевірити, чи збирається воно взагалі, заходимо в термінал і пишемо: $ mvn clean package"Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 6 Якщо у вас так само як тут, все ок: проект зібрався, і джарник вже готовий у target папці. На цьому завдання у рамках опису готове. Все просто так? Тому робимо коміт і пуш у нашу гілку: "Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 7Додаємо на початку опису коміта ім'я нашого завдання, щоб потім було зрозуміло, в рамках якого завдання робилася робота. Натискаємо Commit and Push"Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 8Ще раз переглядаємо та перевіряємо, що саме ми хочемо запушити з локального репозиторію на віддалений і переконавшись, що всі ок, натискаємо Push . Який наступний наш крок? За всіма правилами (які можна почитати в цій статті , в частині про GitHub flow) потрібно створити пулл-реквест на головну гілку та почекати, щоб хтось із команди зробив рецензію коду. Так як я сам, я формально створю пулл-реквест і ще раз все перегляну. Заходжу на сторінку репозиторію, а гітхаб уже знає, що у нас поповнення і пропонує створити пулл-реквест: "Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 9Немає перешкод патріотам (с) — створюємо, як і пропонують. Виставляємо такі ж label, project як і на задачі, в рамках якої працюємо, та заповнюємо опис: "Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 10Натискаємо Create pull request .

Налаштовуємо процес CI

Заходимо до створеного пулл-реквесту: внизу бачимо, що у нас не налаштований Continuous Integration (тут і далі — CI). "Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 11Ну, не налаштований, і що? А навіщо нам взагалі потрібна CI? Що таке CI? Ось приблизно той перелік питань, який має хвилювати нас у цей момент. Загалом і цілому CI- Це безперервний процес зливання коду в загальну кодову базу із запуском складання проекту перед цим. Так званий білд (від англ. build). Щоразу, коли ми збираємо проект, ми запевняємось, що проект пройшов компіляцію, всі його тести пройшли успішно, плюс до CI після складання проекту ще можна додати автотести від тестувальників, які запускаються на цю конкретну збірку. Таким чином вийде, що ми стаємо впевненішими в тому, що нові зміни працюють так, як ми очікуємо, і не ламають попередній функціонал. Також CI хороший тим, що він запускається автоматично після оновлення кодової бази. Тобто ми запушабо у гілку свої зміни та процес пішов — складання, тести, автотести та інші кроки. Якщо якийсь із цих кроків провалився, збірка вважається битою і не може бути влита основна гілка. Саме це ми зараз і зробимо: додамо GitHub Actions, який запускатиме наш код після пуша. GitHub Actions чудово лягає на наш GitHub Flow, тому будемо використовувати його для автоматизації роботи. Цей інструмент дуже потужний і великий, але поки що ми будемо використовувати його тільки для прогонки білда та перевірки, що він збирається як слід. Щоб увімкнути його, знайдемо на сторінці репозиторію кнопкуActions та перейдемо по ній: "Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 12Знаходимо необхідний для нас Continuous Integration workflow: "Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 13Натискаємо Set up this workflow. Далі нам пропонують використовувати їх шаблон: повністю погоджуємося, лише дещо уточнимо все:
# This workflow will build a Java project with Maven
# For more information see: https://help.github.com/actions/language-and-framework-guides/building-and-testing-java-with-maven

name: Java CI with Maven

on:
  push:
    branches: [ main ]
  pull_request:
    branches: [ main ]

jobs:
  build:

    runs-on: ubuntu-latest

    steps:
    - uses: actions/checkout@v2
    - name: Set up JDK 1.8
      uses: actions/setup-java@v1
      with:
        java-version: 1.8
    - name: Build with Maven
      run: mvn -B package --file pom.xml
Тут зазначено, що GitHub Action викликається у двох випадках:
  1. Коли робиться пуш у головну гілку.
  2. Коли створюється пулл-реквест у головну гілку.
У секції jobs описані кроки, які виконуватимуться. У нас лише один крок – build. У ньому видно, що наш проект буде запущений в убунт командою mvn -B package --file pom.xml . Це те, що ми робабо локально. Хочете тут щось змінити – будь ласка. Я використовуватиму цей шаблон, мені його вистачить з головою. Натискаю Start commit , вибираю create a new branch для налаштування процесу і потім Propose new file . Але процес збирання впав… "Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 14Як видно, що Failing after 14s – build. Схоже, щось сталося: переходимо до збирання і дивимося на подробиці:"Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 15Пише, що не знайшов такого пам'ятника. Чому? Аааа, точно! Тому що ми створабо зміни у головній гілці, а нашого завдання там ще немає. І тому він не знайшов пам'ятник… Тому зараз робимо таке: таки мерджимо в майстер ці дані, потім мерджемо main гілку в JRTB-0, і тоді все має пройти відмінно. У пулл-реквесті зі змінами github actions натискаємо Merge pull request : "Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 16І повторюємо Confirm merge . Далі гітхаб пропонує нам видалити гілку, у якій ми працювали. Ми не відмовляємось і видаляємо: "Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 17Далі я не знайшов у пулл-реквесті зі SpringBoot, як стягнути зміни з головної гілки з веб-сайту, тому зробимо це ручками через IDEA.

Крок 1: оновити головну гілку у локальний репозиторій.

В ідеї переходимо на головну гілку, натискаємо ctrl + t і оновлюємо головну гілку:"Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 18

Крок 2: смердити зміни головної гілки в гілку JRTB-0.

Переходимо на JRTB-0 і мерджімо до неї головну."Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 19

Крок 3: запустити зміни.

Натискаємо ctrl+shift+k та підтверджуємо пуш. Тепер чекаємо, коли пройде білд та буде зелений!)) Але він знову червоний. Що таке? Заходимо в логи actions і бачимо, що у нас розсінхрон у версіях джави. У GitHubActions коштує 8, а у нас використовується 11: "Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 20Тепер є два варіанти: або actions підправити, або опустити версію до восьмої. Перший варіант, мені здається, краще та правильніше. Вносимо зміни окремим коммітом: працюватимемо не з 8-ї, а з 11-ї джавою. "Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 21І після цього, нарешті, у нас все вийшло, і ми змогли налаштувати наш процес CI для проекту. Такі речі потрібно налаштовувати на початковому етапі, щоби потім не паритися про це. Тепер уже видно, що білд пройшов і можна мерджити без побоювань:"Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 22

Налаштовуємо роботу з гілками у репозиторії

Ще можна налаштувати в репозиторії такі речі, як правила під час роботи з гілками. Я хочу зробити так, щоб у main гілку не можна було пушити безпосередньо, а тільки через пулл-реквести, і зробити так, щоб не можна було мержити пулл-реквест, якщо не пройшов білд (тобто якщо GitHub Actions впав на якомусь кроці ). Для цього знаходимо кнопку Settings та вибираємо Branches : "Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 23На даний момент немає правил для гілок, тому додамо нове через кнопку Add rule :"Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 24Тут багато налаштувань і кожен може зробити щось під свої потреби. Щоб перед мержем у пулл-реквесті успішно пройшов білд, додаємо галочку в Require status checks to pass before merging та вибираємо статус, який нам потрібний – build. Поки що вистачить: далі можна буде оновлювати це кермо і дивитися, що хочеться ще. Натискаємо Create , щоб створити це кермо. "Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 25Далі, якщо ми знову зайдемо в наш пулл-реквест, можна буде побачити, що тепер наша перевірка має маркування required: "Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 26Перевіримо нашу сторінку з проектом, на якій відображені всі статуси завдань: "Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 27Відразу видно, над яким завданням йде робота. Причому роботу вже зроблено, і завдання знаходиться в code review (рецензія коду) статусу.

Закриваємо JRTB-0

Тепер, коли ми підготували пулл-реквест і зробабо до нього CI, потрібно завершити останній етап: закрити завдання, перенести у правильний статус, подивитися на борді (від англ-board) зміни у нашому проекті. Наш пулл-реквест готовий до того, щоб злити його в майстер. У пулл-реквесті натискаємо кнопку Merge pull request : "Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 28Після успішного Мердж можна видалити, і зазвичай так і роблять. Я цього не робитиму, щоб вам було легше дивитися зміни між гілками/коммітами. Як тільки пулл-реквест смерджен, він автоматично переходить у done у нашому борді проекту: "Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 29Останній крок – закрити завдання (issue) з посиланням на пулл-реквест, в якому це було: "Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 30Це завдання автоматично йде у done на борді. "Java-проект від А до Я": Пишемо проект.  Додаємо SpringBoot і налаштовуємо CI процес - 31Початок покладено, перше завдання зроблено!

Висновки

Здавалося б, ми вже почали працювати та писати код, але все ще налаштування необхідні. Так, це займає час, але воно окупиться стократ, коли проект стане більшим і складнішим і потрібні будуть гарантії, що просто так не вдасться все поламати одним коммітом. Пулл-реквест, у якому все це відбувається, доступний тут . Можливо, коли ви читатимете, він буде вже закритий. Це не страшно: вся потрібна інформація зберігатиметься за посиланням. Дякую всім за читання, до швидкої зустрічі. Дальше більше!

Список всіх матеріалів серії на початку цієї статті.

Коментарі
ЩОБ ПОДИВИТИСЯ ВСІ КОМЕНТАРІ АБО ЗАЛИШИТИ КОМЕНТАР,
ПЕРЕЙДІТЬ В ПОВНУ ВЕРСІЮ