Русский
Русский
English
Статистика
Реклама

Nuke. Быстрый старт

Послепрочтениястатьи"КакготовитьCake,используятолькоFrosting"мнепришлавголову мысль:"Какойбольшойпроектдлятакогопростогопроцессасборки".Послеэтогояирешилнаписатьмини-статьюпроаналогCakeNuke.

Если я правильно понимаю историю проекта, Nuke появился как более простой и удобный аналог Cake, Psake и Fake. Автору Nuke хотелось писать скрипты сборки именно на C#, поэтому ему не подошли Psake и Fake. Судя по всему, когда создавался Nuke, не существовал Frosting, и все Cake скрипты были странными файлами с DSL на основе C#, которые можно было писать и отлаживать только в VS Code. Скрипт сборки Nuke изначально задумывался как обычное консольное приложение, которое легко можно писать и отлаживать в любой IDE.

ДавайтесоздадимпростейшийскриптсборкинаNukeисоберёмсегопомощьюприложение!

1. Создаёмприложение

Создадим новое приложение в папке src репозитория. Это не обязательно, но далее станет понятно, почему удобнее использовать для этого отдельную папку.

2. Устанавливаем Global Tool

dotnet tool install Nuke.GlobalTool --global

3. Создаём проект со скриптом сборки

Дляэтогонеобходимовыполнитькоманду:

nuke :setup

Это запустит консольный конфигуратор проекта сборки. Привожу анимацию его работы из документации Nuke.

Давайте посмотрим, что изменилось в репозитории:

Если не трогать настройки по умолчанию, то скрипт установки nuke создаст проект сборки в отдельной папке build репозитория. Таким образом, скрипты сборки лежат в build, а исходники в src. Те же настройки по умолчанию предполагают использование папки output в корне репозитория в качестве выходной директории для сборки.

Разберём изменения по отдельности:

  • .nuke файл-маркер, по которому nuke определяет корневую папку

  • build.* бутстрапперы для запуска сборки. При необходимости могут и .net установить, если его нет на машине, на которой происходит сборка

  • _build.csproj файл проекта сборки. Имеет такое странное название для того, чтобы всегда быть первым в списке проектов в Solution Explorer

  • .editorconfig и _build.csproj.DotSettings просто настройки стиля

А теперь самое интересное:

3.1. Изменения в sln

Проект _build был добавлен в решение. Но был добавлен очень хитрым способом. Он отображается в IDE, его можно собрать, но если выполнить сборку всего решения, то мы увидим следующий вывод:

1>------ Rebuild All started: Project: Demo, Configuration: Debug Any CPU ------2>------ Skipped Rebuild All: Project: _build, Configuration: Debug Any CPU ------2>Project not selected to build for this solution configuration 1>Demo -> C:\Users\buldo\source\repos\nuke-example\src\Demo\Demo\bin\Debug\netcoreapp3.1\Demo.dll========== Rebuild All: 1 succeeded, 0 failed, 1 skipped ==========

То есть при пересборке решения проект _build не собирается. Действительно, если бы скрипт сборки при работе вызывал ещё и пересборку самого себя, это могло бы привести к проблемам.

3.2. Build.cs

Приведу полный код сгенерированного файла и объясню основные моменты.

[CheckBuildProjectConfigurations][ShutdownDotNetAfterServerBuild]class Build : NukeBuild{    public static int Main () => Execute<Build>(x => x.Compile);    [Parameter("Configuration to build - Default is 'Debug' (local) or 'Release' (server)")]    readonly Configuration Configuration = IsLocalBuild ? Configuration.Debug : Configuration.Release;    [Solution] readonly Solution Solution;    [GitRepository] readonly GitRepository GitRepository;    [GitVersion] readonly GitVersion GitVersion;    AbsolutePath SourceDirectory => RootDirectory / "src";    AbsolutePath OutputDirectory => RootDirectory / "output";    Target Clean => _ => _        .Before(Restore)        .Executes(() =>        {            SourceDirectory.GlobDirectories("**/bin", "**/obj").ForEach(DeleteDirectory);            EnsureCleanDirectory(OutputDirectory);        });    Target Restore => _ => _        .Executes(() =>        {            DotNetRestore(s => s                .SetProjectFile(Solution));        });    Target Compile => _ => _        .DependsOn(Restore)        .Executes(() =>        {            DotNetBuild(s => s                .SetProjectFile(Solution)                .SetConfiguration(Configuration)                .SetAssemblyVersion(GitVersion.AssemblySemVer)                .SetFileVersion(GitVersion.AssemblySemFileVer)                .SetInformationalVersion(GitVersion.InformationalVersion)                .EnableNoRestore());        });}

Данный класс является точкой входа в приложения. В методе Main запускается сборка и выбирается цель сборки по умолчанию.

Цели сборки представлены свойствами типа Target. Синтаксис с кучей стрелочек сначала пугает, но потом привыкаешь. Для целей сборки можно задавать зависимости (DependsOn()), явный порядок выполнения (Before(), After()), условия выполнения (как статические, так и динамические), а главное указывать с помощью Executes(), что вообще делает этот Target.

Следующая важная вещь для начинающего пользователя Nuke параметры сборки. Достаточно просто пометить поле атрибутом [Parameter], и можно передавать значение этого поля через командную строку. В данном случае конфигурацию сборки Debug или Release. Механизм очень гибок можно сделать параметр необходимым, и без него сборка не запустится. Также параметр можно делать необходимым только для конкретного Target.

Nuke предоставляет необходимые абстракции над решениями и проектами. Несколько решений в проекте? Нет проблем. Добавьте новое свойство типа Solution и пометьте его атрибутом [Solution] Nuke найдёт решение, распарсит его и предоставит доступ его содержимому.

Также в этом файле можно заметить пример расширения Nuke модуль для работы с git установлен отдельным пакетом. С помощью полей GitRepository и GitVersion можно легко оперировать состоянием репозитория. Например, ориентируясь на имя ветки (master/не master), выбрать ставить или нет preview метку при сборке nuget пакета.

4. Запуск сборки

Сборка запускается с помощью бутстраппера:

.\build.ps1 [targets] [arguments]

В данном случае для того, чтобы собрать приложение, необходимо выполнить следующую команду:

.\build.ps1 --target Compile --configuration release

На выходе получаем лог сборки, завершающийся удобной статистикой:

TargetStatusDurationRestoreExecuted0:01CompileExecuted0:03Total0:04Build succeeded on 29.12.2020 21:38:10.

На самом деле, если установлен NET 5, сборка скорее всего завершится ошибкой. Волшебный фикс заменить атрибут поля GitVersion на [GitVersion(Framework = "netcoreapp3.1")].

5. Делаем что-то полезное

По самому первому скриншоту статьи можно было заметить, что был создан проект на Avalonia. Так давайте соберём наше приложение, да так, чтобы оно было в виде одного исполняемого файла, включающего рантайм. Это значит, что придётся собирать несколько исполняемых файлов.

Далее я приведу код цели сборки с подробными комментариями:

Target Publish => _ => _    .Executes(() =>    {        var rids = new[] {"win-x64", "linux-x64"}; // Перечисляем RID'ы, для которых собираем приложение        DotNetPublish(s => s // Теперь вызываем dotnet publish            .SetAssemblyVersion(GitVersion.AssemblySemVer)            .SetFileVersion(GitVersion.AssemblySemFileVer)            .SetInformationalVersion(GitVersion.InformationalVersion)            .SetProject(Solution.GetProject("Demo")) // Для dotnet publish желательно указывать проект            .SetPublishSingleFile(true) // Собираем в один файл            .SetSelfContained(true)     // Вместе с рантаймом            .SetConfiguration(Configuration) // Для определённой конфигурации            .CombineWith(rids, (s, rid) => s // Но нам нужны разные комбинации параметров                .SetRuntime(rid) // Устанавливаем RID                .SetOutput(OutputDirectory/rid))); // Делаем так, чтобы сборки с разными RID попали в разные папки    });

Заключение

Nuke удобная система сборки. Она проста и минималистична в начале вашего проекта, но достаточно мощна для того, чтобы развиваться вместе с ним.

Источник: habr.com
К списку статей
Опубликовано: 19.01.2021 10:15:06
0

Сейчас читают

Комментариев (0)
Имя
Электронная почта

Net

C

Nuke

Ci/cd

Категории

Последние комментарии

  • Имя: Макс
    24.08.2022 | 11:28
    Я разраб в IT компании, работаю на арбитражную команду. Мы работаем с приламы и сайтами, при работе замечаются постоянные баны и лаги. Пацаны посоветовали сервис по анализу исходного кода,https://app Подробнее..
  • Имя: 9055410337
    20.08.2022 | 17:41
    поможем пишите в телеграм Подробнее..
  • Имя: sabbat
    17.08.2022 | 20:42
    Охренеть.. это просто шикарная статья, феноменально круто. Большое спасибо за разбор! Надеюсь как-нибудь с тобой связаться для обсуждений чего-либо) Подробнее..
  • Имя: Мария
    09.08.2022 | 14:44
    Добрый день. Если обладаете такой информацией, то подскажите, пожалуйста, где можно найти много-много материала по Yggdrasil и его уязвимостях для написания диплома? Благодарю. Подробнее..
© 2006-2024, personeltest.ru