1

Цель

Мы хотим настроить автоматические сборки для наших проектов Unity, используя MSBuild и MSBuild-Plug-In на Jenkins.

Моя конфигурация

Соответственно Build-Step выглядит

Build a Visual Studio project or solution using MSBuild


MSBuild Version                    VisualStudio-MSBuild-15

MSBuild Build File                 E:\Jenkins\workspace\000_BUILD\<MyProjectName>

Command Line Arguments             /m /p:Configuration=Release /p:Plattform=x86

Pass build variables as properties [x]

Do not use chcp command            [ ]

и конфигурация MSBuild Конфигурация MSBuild

где я использую MSBuild из нашей установки VisualStudio 2017.
Это приводит в итоге к пакетной команде, такой как

cmd.exe /C " chcp 1252 & E:\VisualStudio\MSBuild\15.0\Bin\msbuild.exe /m /p:Configuration=Release /p:Platform=x86 "E:\Jenkins\workspace\000_BUILDS\MY_PROJECT\My Project.sln" " && exit %%ERRORLEVEL%%

Просто скажу это, чтобы прояснить, что мой вопрос напрямую не зависит от Дженкинса.


Моя проблема:

Я получаю 72 сообщения об ошибках, большинство из которых выглядят как (перевод с немецкого)

2> Properties\AssemblyInfo.cs(8,12): ошибка CS0246: тип или пространство имен "AssemblyTitleAttribute" не найдены (возможно, отсутствует директива using или ссылка на сборку).

некоторым из них тоже нравится (перевод с немецкого)

2> Свойства \AssemblyInfo.cs(9,32): ошибка CS0518: предопределенный тип «Система.Строка "не определена или не импортирована.


Может быть, намек? Если я создаю тот же проект (я остановил задание jenkins после завершения извлечения из git) непосредственно в VisualStudio, он выдает 2 предупреждения о некоторых устаревших вызовах, но AppPackage создается без каких-либо ошибок.

И странная вещь:
После того, как я успешно собрал проект в VisualStudio, я также могу построить проект с использованием MSBuild из командной строки, получить тот же вывод (2 предупреждения, но без ошибок) и собрать свой AppPackage.


ВОПРОС

Что я делаю неправильно?
Чем VisualStudio из GUI отличается от MSBuild из командной строки?
Возможно, мне не хватает шага или опции для MSbuild?

1 ответ1

1

Проблема была в том, что я не восстанавливал Nuget-Packages перед сборкой с использованием MSBuild. (При открытии Visual-Studio в графическом интерфейсе кажется, что этот шаг выполняется автоматически.)

Итак, вот полное решение от Unity-проекта до пакета приложений Holo-Lens, которое наконец-то сработало для меня:

Создать пакет Unity CommandLineBuild

Прежде всего, чтобы иметь возможность создавать Unity-проект через командную строку, вам нужен специальный класс.

Это должно быть размещено в /Assets/Editor вашего проекта:

using UnityEngine;
using UnityEditor;
using System.Collections;
using System.Collections.Generic;
using System;

namespace JENKINS
{
    public class AutoBuilder : ScriptableObject
    {
        static string[] SCENES = FindEnabledEditorScenes();

        // Use real app name here
        /* Anyway the App will have the name as configured within the Unity-Editor
           This Appname is just for the Folder in which to Build */
        static string APP_NAME;
        static string TARGET_DIR;

        [MenuItem("Custom/CI/Windows Mixed Reality Build (UWP)")]
        public static void PerformWindowsMixedRealityBuild()
        {
            APP_NAME = GetArg("-appName");
            TARGET_DIR = GetArg("-buildFolder");
            Debug.Log("Jenkins-Build: APP_NAME: " + APP_NAME + " TARGET_DIR: " + TARGET_DIR);

            GenericBuild(SCENES, TARGET_DIR + "/" + APP_NAME, BuildTargetGroup.WSA, BuildTarget.WSAPlayer, BuildOptions.AllowDebugging);
        }

        private static string[] FindEnabledEditorScenes()
        {
            List<string> EditorScenes = new List<string>();

            foreach (EditorBuildSettingsScene scene in EditorBuildSettings.scenes)
            {
                if (!scene.enabled) continue;
                EditorScenes.Add(scene.path);
            }

            return EditorScenes.ToArray();
        }

        private static void GenericBuild(string[] scenes, string app_target, BuildTargetGroup build_target_group, BuildTarget build_target, BuildOptions build_options)
        {
            EditorUserBuildSettings.SwitchActiveBuildTarget(build_target_group, BuildTarget.WSAPlayer);

            string res = BuildPipeline.BuildPlayer(scenes, app_target, build_target, build_options);
            if (res.Length > 0)
            {
                throw new Exception("BuildPlayer failure: " + res);
            }
        }

        /**
         * Get Arguments from the command line by name
         */
        private static string GetArg(string name)
        {
            var args = System.Environment.GetCommandLineArgs();

            for (int i = 0; i < args.Length; i++)
            {
                if (args[i] == name && args.Length > i + 1)
                {
                    return args[i + 1];
                }
            }

            return null;
        }
    }
}

Но так как вы не хотите импортировать этот пакет в каждый ваш проект, пусть Jenkins импортирует его на лету.

Для этого я создал класс в пустом проекте. AutoBuilder.cs в пустом Unity-проекте

и экспортируйте его как AutoBuilder.unityproject:

  1. щелкните правой кнопкой мыши на Assets и выберите Export package...
  2. Выберите место для сохранения
    (Я помещаю мой в E:\UnityPackage\AutoBuilder.unitypackage .)

Шаги сборки

Unity-Plugin и MSBuild-Plugin у меня не сработали, поэтому я делаю каждый шаг в отдельном Batch-файле.

1. Импорт пакета AutoBuild.unity в проект

Сначала нам нужно импортировать пакет before create unity to клонированный проект.

Бежать

<\Path\To\Your\Unity\Installation\>Editor\Unity.exe -quit -batchmode -username 'xxxxxxxxxxxxx' -password 'xxxxxxxxxxx' -logFile uniytImportLog.txt -importPackage E:\UnityPackage\AutoBuilder.unitypackage

Unity - Manual: аргументы командной строки

  • -quit: сделать выход из Unity после завершения импорта
  • -batchmode: не открывать / загружать графический интерфейс и сразу выходить из 1 при любой ошибке
  • (опционально)-username и -password Введите учетные данные так Unity может поиск вашей лицензии ( в случае необходимости)
  • (необязательно)-logFile: записать вывод в файл журнала (поскольку Unity в пакетном режиме не будет отображать его!)
  • -importPackage: наконец, сообщите Unity, что делать; в этом случае импортируйте наш файл unitypackage (измените его на место, в котором вы сохранили AutoBuilder.unitypackage )

2. Запустите Unity-Build для Visual-Studio-Solution (.sln)

Теперь проект готов для сборки через командную строку для решения .sln .

Бежать

<\Path\To\Your\Unity\Installation\>Editor\Unity.exe -quit -batchmode -username 'xxxxxxxxxxxxx' -password 'xxxxxxxxxxx' -logFile uniytBuildLog.txt -buildTarget wsaplayer -executeMethod JENKINS.AutoBuilder.PerformWindowsMixedRealityBuild  -appName %JOB_NAME% -buildFolder %WORKSPACE%\00_BUILD

Unity - Manual: аргументы командной строки

  • -quit: сделать выход из Unity после завершения импорта
  • -batchmode: не открывать / загружать графический интерфейс и сразу выходить из 1 при любой ошибке
  • (опционально)-username и -password Введите учетные данные так Unity может поиск вашей лицензии ( в случае необходимости)
  • (необязательно)-logFile: записать вывод в файл журнала (поскольку Unity в пакетном режиме не будет отображать его!)
  • -buildTarget: переключиться на соответствующую цель сборки перед загрузкой проекта. Для пакетов приложений это, например, wsaplayer
  • -executeMethod: наконец сказать Unity, что делать; в этом случае выполните метод из нашего ранее импортированного класса AutoBuilder
  • -appName %JOB_NAME% и -buildFolder %WORKSPACE%\00_BUILD: вызываемый нами метод принимает / требует аргументы из командной строки.
    • -appName звучит немного обманчиво, так как на самом деле это только подпапка, в которую будет собираться Unity. %JOB_NAME% - это глобальная переменная среды Jenkins для фактического имени задания.
    • -buildFolder - главная папка, в которую будет собираться Unity. %WORKSPACE% - это глобальная переменная среды Jenkins для папки рабочего пространства фактического задания.

НОТА
Перед последними двумя последними шагами вы должны знать, как файл .sln вызывается после Unity-Build.

Я предполагаю, что что-то вроде YourProject.sln хранится в переменной App_Name потому что это определено в Unity:

Зайдите в Редактировать -> Настройки проекта -> Настройки плеера Зайдите в Редактировать -> Настройки проекта -> Настройки плеера и измените Product Name Изменить название продукта


3. Восстановление Nuget-пакетов (это был в основном шаг, который я пропустил раньше)

Чтобы восстановить nuget-пакеты (Visual-Studio обычно делает это автоматически при открытии решения в графическом интерфейсе), запустите

cmd.exe /C " chcp 1252 & <Path\To\Your\Visual-Studio\Installation>\MSBuild\15.0\Bin\msbuild.exe /m /t:restore /p:Configuration=Release /p:Platform=x86 "%WORKSPACE%\00_BUILD\%JOB_NAME%\%App_Name%" "

Справочник по командной строке MSBuild

  • /m: Определяет максимальное количество одновременных процессов для использования при сборке. Если вы не включите этот переключатель, значением по умолчанию будет 1. Если вы включите этот переключатель без указания значения, MSBuild будет использовать до числа процессоров в компьютере.
  • /t: Построить указанные цели в проекте.
  • /p: установить или переопределить указанные свойства уровня проекта, где name - это имя свойства, а value - значение свойства. (-> для Holo-Lens это Configuration=Release и Plattform=x86)
  • WORKSPACE: глобальная переменная среды Jenkins для папки рабочего пространства фактического задания
  • 00_BUILD: мы передали это как параметр -buildFolder на шаг сборки Unity.
  • JOB_NAME: глобальная переменная среды Jenkins для фактического имени задания
  • App_Name: как уже упоминалось перед именем построенного Visual-Studio-Solution (.sln)

Это только сделает восстановление и пока не построит проект.

4. Создайте окончательный пакет приложений с помощью MSBuild

Мне не понравился MSBuild-Plugin для jenkins, поэтому я сделал это в командном файле и использовал команду, которая была создана плагином раньше. Но выполнение этого в командном файле дало мне больше гибкости с точки зрения определения, например, целевого файла.

cmd.exe /C " chcp 1252 & <Path\To\Your\Visual-Studio\Installation>\MSBuild\15.0\Bin\msbuild.exe /m /t:restore /p:Configuration=Release /p:Platform=x86 "%WORKSPACE%\00_BUILD\%JOB_NAME%\%App_Name%" "

Справочник по командной строке MSBuild

  • /m: Определяет максимальное количество одновременных процессов для использования при сборке. Если вы не включите этот переключатель, значением по умолчанию будет 1. Если вы включите этот переключатель без указания значения, MSBuild будет использовать до числа процессоров в компьютере.
  • /t: Построить указанные цели в проекте.
  • /p: установить или переопределить указанные свойства уровня проекта, где name - это имя свойства, а value - значение свойства. (-> для Holo-Lens это Configuration=Release и Plattform=x86)
  • WORKSPACE: глобальная переменная среды Jenkins для папки рабочего пространства фактического задания
  • 00_BUILD: мы передали это как параметр -buildFolder на шаг сборки Unity.
  • JOB_NAME: глобальная переменная среды Jenkins для фактического имени задания
  • App_Name: как уже упоминалось перед именем построенного Visual-Studio-Solution (.sln)

После завершения вы должны иметь окончательный пакет приложений под

%WORKSPACE%\000_BUILD\%JOB_NAME%\%App_Name%\AppPackages

Всё ещё ищете ответ? Посмотрите другие вопросы с метками .