Skip to content

Commit 3e9508c

Browse files
committed
Test custom build script
1 parent cf0b1c2 commit 3e9508c

6 files changed

Lines changed: 253 additions & 1 deletion

File tree

.github/workflows/main.yml

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -42,7 +42,8 @@ jobs:
4242
buildsPath: Build
4343
projectPath: ${{ matrix.projectPath }}
4444
targetPlatform: ${{ matrix.targetPlatform }}
45-
customParameters: -Development
45+
customParameters: -Development -test SomeValue
46+
buildMethod: UnityBuilderAction.BuildScript.Build
4647
- uses: actions/upload-artifact@v3
4748
with:
4849
name: Build-${{ matrix.targetPlatform }}

Samples/AppKit Sample/Assets/Editor.meta

Lines changed: 3 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Samples/AppKit Sample/Assets/Editor/UnityBuilderAction.meta

Lines changed: 3 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.
Lines changed: 233 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,233 @@
1+
using System;
2+
using System.Collections.Generic;
3+
using System.IO;
4+
using System.Linq;
5+
using UnityEditor;
6+
using UnityEditor.Build.Reporting;
7+
8+
namespace UnityBuilderAction
9+
{
10+
public static class BuildScript
11+
{
12+
private static readonly string Eol = Environment.NewLine;
13+
14+
private static readonly string[] Secrets =
15+
{"androidKeystorePass", "androidKeyaliasName", "androidKeyaliasPass", "test"};
16+
17+
public static void Build()
18+
{
19+
// Gather values from args
20+
Dictionary<string, string> options = GetValidatedOptions();
21+
22+
if(options.TryGetValue("test", out string test))
23+
{
24+
Console.WriteLine($"Test argument: {test}");
25+
}
26+
27+
// Set version for this build
28+
if(options.TryGetValue("buildVersion", out string buildVersion) && buildVersion != "none")
29+
{
30+
PlayerSettings.bundleVersion = buildVersion;
31+
PlayerSettings.macOS.buildNumber = buildVersion;
32+
}
33+
if(options.TryGetValue("androidVersionCode", out string versionCode) && versionCode != "0")
34+
{
35+
PlayerSettings.Android.bundleVersionCode = int.Parse(options["androidVersionCode"]);
36+
}
37+
38+
// Apply build target
39+
var buildTarget = (BuildTarget) Enum.Parse(typeof(BuildTarget), options["buildTarget"]);
40+
switch (buildTarget)
41+
{
42+
case BuildTarget.Android:
43+
{
44+
EditorUserBuildSettings.buildAppBundle = options["customBuildPath"].EndsWith(".aab");
45+
if (options.TryGetValue("androidKeystoreName", out string keystoreName) &&
46+
!string.IsNullOrEmpty(keystoreName))
47+
{
48+
PlayerSettings.Android.useCustomKeystore = true;
49+
PlayerSettings.Android.keystoreName = keystoreName;
50+
}
51+
if (options.TryGetValue("androidKeystorePass", out string keystorePass) &&
52+
!string.IsNullOrEmpty(keystorePass))
53+
PlayerSettings.Android.keystorePass = keystorePass;
54+
if (options.TryGetValue("androidKeyaliasName", out string keyaliasName) &&
55+
!string.IsNullOrEmpty(keyaliasName))
56+
PlayerSettings.Android.keyaliasName = keyaliasName;
57+
if (options.TryGetValue("androidKeyaliasPass", out string keyaliasPass) &&
58+
!string.IsNullOrEmpty(keyaliasPass))
59+
PlayerSettings.Android.keyaliasPass = keyaliasPass;
60+
if (options.TryGetValue("androidTargetSdkVersion", out string androidTargetSdkVersion) &&
61+
!string.IsNullOrEmpty(androidTargetSdkVersion))
62+
{
63+
var targetSdkVersion = AndroidSdkVersions.AndroidApiLevelAuto;
64+
try
65+
{
66+
targetSdkVersion =
67+
(AndroidSdkVersions) Enum.Parse(typeof(AndroidSdkVersions), androidTargetSdkVersion);
68+
}
69+
catch
70+
{
71+
UnityEngine.Debug.Log("Failed to parse androidTargetSdkVersion! Fallback to AndroidApiLevelAuto");
72+
}
73+
74+
PlayerSettings.Android.targetSdkVersion = targetSdkVersion;
75+
}
76+
77+
break;
78+
}
79+
case BuildTarget.StandaloneOSX:
80+
PlayerSettings.SetScriptingBackend(BuildTargetGroup.Standalone, ScriptingImplementation.Mono2x);
81+
break;
82+
}
83+
84+
// Determine subtarget
85+
int buildSubtarget = 0;
86+
#if UNITY_2021_2_OR_NEWER
87+
if (!options.TryGetValue("standaloneBuildSubtarget", out var subtargetValue) || !Enum.TryParse(subtargetValue, out StandaloneBuildSubtarget buildSubtargetValue)) {
88+
buildSubtargetValue = default;
89+
}
90+
buildSubtarget = (int) buildSubtargetValue;
91+
#endif
92+
93+
// Custom build
94+
Build(buildTarget, buildSubtarget, options["customBuildPath"]);
95+
}
96+
97+
private static Dictionary<string, string> GetValidatedOptions()
98+
{
99+
ParseCommandLineArguments(out Dictionary<string, string> validatedOptions);
100+
101+
if (!validatedOptions.TryGetValue("projectPath", out string _))
102+
{
103+
Console.WriteLine("Missing argument -projectPath");
104+
EditorApplication.Exit(110);
105+
}
106+
107+
if (!validatedOptions.TryGetValue("buildTarget", out string buildTarget))
108+
{
109+
Console.WriteLine("Missing argument -buildTarget");
110+
EditorApplication.Exit(120);
111+
}
112+
113+
if (!Enum.IsDefined(typeof(BuildTarget), buildTarget ?? string.Empty))
114+
{
115+
Console.WriteLine($"{buildTarget} is not a defined {nameof(BuildTarget)}");
116+
EditorApplication.Exit(121);
117+
}
118+
119+
if (!validatedOptions.TryGetValue("customBuildPath", out string _))
120+
{
121+
Console.WriteLine("Missing argument -customBuildPath");
122+
EditorApplication.Exit(130);
123+
}
124+
125+
const string defaultCustomBuildName = "TestBuild";
126+
if (!validatedOptions.TryGetValue("customBuildName", out string customBuildName))
127+
{
128+
Console.WriteLine($"Missing argument -customBuildName, defaulting to {defaultCustomBuildName}.");
129+
validatedOptions.Add("customBuildName", defaultCustomBuildName);
130+
}
131+
else if (customBuildName == "")
132+
{
133+
Console.WriteLine($"Invalid argument -customBuildName, defaulting to {defaultCustomBuildName}.");
134+
validatedOptions.Add("customBuildName", defaultCustomBuildName);
135+
}
136+
137+
return validatedOptions;
138+
}
139+
140+
private static void ParseCommandLineArguments(out Dictionary<string, string> providedArguments)
141+
{
142+
providedArguments = new Dictionary<string, string>();
143+
string[] args = Environment.GetCommandLineArgs();
144+
145+
Console.WriteLine(
146+
$"{Eol}" +
147+
$"###########################{Eol}" +
148+
$"# Parsing settings #{Eol}" +
149+
$"###########################{Eol}" +
150+
$"{Eol}"
151+
);
152+
153+
// Extract flags with optional values
154+
for (int current = 0, next = 1; current < args.Length; current++, next++)
155+
{
156+
// Parse flag
157+
bool isFlag = args[current].StartsWith("-");
158+
if (!isFlag) continue;
159+
string flag = args[current].TrimStart('-');
160+
161+
// Parse optional value
162+
bool flagHasValue = next < args.Length && !args[next].StartsWith("-");
163+
string value = flagHasValue ? args[next].TrimStart('-') : "";
164+
bool secret = Secrets.Contains(flag);
165+
string displayValue = secret ? "*HIDDEN*" : "\"" + value + "\"";
166+
167+
// Assign
168+
Console.WriteLine($"Found flag \"{flag}\" with value {displayValue}.");
169+
providedArguments.Add(flag, value);
170+
}
171+
}
172+
173+
private static void Build(BuildTarget buildTarget, int buildSubtarget, string filePath)
174+
{
175+
string[] scenes = EditorBuildSettings.scenes.Where(scene => scene.enabled).Select(s => s.path).ToArray();
176+
var buildPlayerOptions = new BuildPlayerOptions
177+
{
178+
scenes = scenes,
179+
target = buildTarget,
180+
// targetGroup = BuildPipeline.GetBuildTargetGroup(buildTarget),
181+
locationPathName = filePath,
182+
// options = UnityEditor.BuildOptions.Development
183+
#if UNITY_2021_2_OR_NEWER
184+
subtarget = buildSubtarget
185+
#endif
186+
};
187+
188+
BuildSummary buildSummary = BuildPipeline.BuildPlayer(buildPlayerOptions).summary;
189+
ReportSummary(buildSummary);
190+
ExitWithResult(buildSummary.result);
191+
}
192+
193+
private static void ReportSummary(BuildSummary summary)
194+
{
195+
Console.WriteLine(
196+
$"{Eol}" +
197+
$"###########################{Eol}" +
198+
$"# Build results #{Eol}" +
199+
$"###########################{Eol}" +
200+
$"{Eol}" +
201+
$"Duration: {summary.totalTime.ToString()}{Eol}" +
202+
$"Warnings: {summary.totalWarnings.ToString()}{Eol}" +
203+
$"Errors: {summary.totalErrors.ToString()}{Eol}" +
204+
$"Size: {summary.totalSize.ToString()} bytes{Eol}" +
205+
$"{Eol}"
206+
);
207+
}
208+
209+
private static void ExitWithResult(BuildResult result)
210+
{
211+
switch (result)
212+
{
213+
case BuildResult.Succeeded:
214+
Console.WriteLine("Build succeeded!");
215+
EditorApplication.Exit(0);
216+
break;
217+
case BuildResult.Failed:
218+
Console.WriteLine("Build failed!");
219+
EditorApplication.Exit(101);
220+
break;
221+
case BuildResult.Cancelled:
222+
Console.WriteLine("Build cancelled!");
223+
EditorApplication.Exit(102);
224+
break;
225+
case BuildResult.Unknown:
226+
default:
227+
Console.WriteLine("Build result is unknown!");
228+
EditorApplication.Exit(103);
229+
break;
230+
}
231+
}
232+
}
233+
}

Samples/AppKit Sample/Assets/Editor/UnityBuilderAction/BuildScript.cs.meta

Lines changed: 3 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Samples/AppKit Sample/Assets/Scripts/AppInit.cs

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,5 @@
1+
using System;
2+
using System.Collections;
13
using Skibitsky.Unity;
24
using UnityEngine;
35
using UnityEngine.SceneManagement;
@@ -14,6 +16,13 @@ public class AppInit : MonoBehaviour
1416
private void Start()
1517
{
1618
InitDebugConsole();
19+
20+
Debug.Log("Environment Variables:");
21+
foreach (DictionaryEntry de in Environment.GetEnvironmentVariables())
22+
{
23+
Debug.Log($"{de.Key} = {de.Value}");
24+
}
25+
1726
SceneManager.LoadScene(_mainScene);
1827
}
1928

0 commit comments

Comments
 (0)