Skip to content

Commit a5c4a10

Browse files
fix: detect compressed builds
1 parent 4ba6dfa commit a5c4a10

4 files changed

Lines changed: 175 additions & 17 deletions

File tree

.editorconfig

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -213,6 +213,7 @@ csharp_preserve_single_line_blocks = true
213213
csharp_wrap_ternary_expr_style = wrap_if_long
214214

215215
## ReSharper
216+
csharp_indent_nested_foreach_stmt = true
216217
csharp_empty_block_style = together
217218
csharp_trailing_comma_in_multiline_lists = true:warning
218219
csharp_trailing_comma_in_singleline_lists = false:warning

Editor/ElympicsWebIntegration.cs

Lines changed: 31 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -311,6 +311,7 @@ private static void GetAvailableRegionsHandler(Action<List<RegionResponseModel>>
311311
updateProperty?.Invoke(availableRegions.Regions.ToList());
312312
return;
313313
}
314+
314315
onFailure?.Invoke();
315316
}
316317

@@ -452,10 +453,9 @@ void OnContinuation(bool success)
452453
GameUploadedToTheCloud?.Invoke();
453454
});
454455
}
455-
456456
}
457457

458-
private static string[] compoundExtensions =
458+
internal static string[] compoundExtensions =
459459
{
460460
".framework.js",
461461
".wasm",
@@ -471,11 +471,14 @@ private static bool TryGetFullExtension(ReadOnlySpan<char> fileName, string[] kn
471471
compoundExtension = string.Empty;
472472
foreach (var ext in knownCompoundExtensions)
473473
{
474-
if (!fileName.EndsWith(ext.AsSpan(), StringComparison.OrdinalIgnoreCase))
474+
var extIndex = fileName.IndexOf(ext.AsSpan(), StringComparison.OrdinalIgnoreCase);
475+
if (extIndex < 0)
475476
continue;
476-
compoundExtension = ext;
477+
478+
compoundExtension = fileName[extIndex..].ToString();
477479
return true;
478480
}
481+
479482
return false;
480483
}
481484

@@ -486,6 +489,21 @@ private static bool DoesFileHaveGivenCompoundExtension(string fileName, string c
486489
return false;
487490
}
488491

492+
internal static List<(string name, string extension)> GetValidFiles(string[] fileNames, string[] knownCompoundExtensions)
493+
{
494+
return fileNames.Select(fileName =>
495+
{
496+
if (TryGetFullExtension(fileName.AsSpan(), knownCompoundExtensions, out var compoundExtension))
497+
{
498+
var splitExtension = compoundExtension.Split('.');
499+
var split = fileName.Split('.');
500+
var name = string.Join(".", split.Take(split.Length - splitExtension.Length + 1));
501+
return (name, compoundExtension);
502+
}
503+
504+
return (string.Empty, string.Empty);
505+
}).Where(file => !string.IsNullOrEmpty(file.Item1)).ToList();
506+
}
489507

490508
public static void UploadClientBuild(string clientBuildPath, string gameId, string clientGameVersion, string serverGameVersion, string streamingAssetsUrl)
491509
{
@@ -517,25 +535,21 @@ void OnCheckAuthTokenAndRefreshIfNeededContinuation(bool success)
517535

518536
var filePaths = Directory.GetFiles(clientBuildPath);
519537
var fileNames = filePaths.Select(Path.GetFileName).ToArray();
520-
var validFiles = fileNames.Select(fileName =>
521-
{
522-
if (TryGetFullExtension(fileName.AsSpan(), compoundExtensions, out var compoundExtension))
523-
{
524-
var name = fileName.Split('.').First();
525-
return (name, compoundExtension);
526-
}
527-
return (string.Empty, string.Empty);
538+
var validFiles = GetValidFiles(fileNames, compoundExtensions);
528539

529-
}).Where(file => !string.IsNullOrEmpty(file.Item1)).ToList();
530-
531-
//TO DO: make sure all necessary files are present
540+
if (validFiles.Count != compoundExtensions.Length)
541+
{
542+
throw new ElympicsException(
543+
$"Not all required files will be uploaded to bucket{Environment.NewLine}Files in directory: {string.Join('|', fileNames)}{Environment.NewLine}Validated files: {string.Join('|', validFiles)}");
544+
}
532545

533546
if (!ElympicsConfig.IsLogin)
534547
{
535548
ElympicsLogger.LogError("You must be logged in Elympics to upload a client build.");
536549
EditorUtility.ClearProgressBar();
537550
return;
538551
}
552+
539553
EditorUtility.DisplayProgressBar(title, "Initializing upload", 0.1f);
540554

541555
var request = new ClientBuildUploadInitRequestModel()
@@ -544,7 +558,7 @@ void OnCheckAuthTokenAndRefreshIfNeededContinuation(bool success)
544558
clientGameVersion = clientGameVersion,
545559
serverGameVersion = serverGameVersion,
546560
streamingAssetsUrl = streamingAssetsUrl,
547-
files = validFiles.Select(fileNameAndExtension => FixedPrefix + fileNameAndExtension.Item2).ToArray(),
561+
files = validFiles.Select(fileNameAndExtension => FixedPrefix + fileNameAndExtension.extension).ToArray(),
548562
};
549563

550564
var uri = GetCombinedUrl(ElympicsWebEndpoint, "client-builds", "init");
@@ -588,7 +602,6 @@ void OnClientBuildUploadInitResponse(ClientBuildUploadInitResponseModel response
588602
{
589603
for (var index = 0; index < response.Files.Length; index++)
590604
{
591-
592605
var fileUploadInfo = response.Files[index];
593606
var responseFile = Path.Combine(clientBuildPath, fileUploadInfo.FilePath);
594607
var expectedFile = validFiles[index];
@@ -602,6 +615,7 @@ void OnClientBuildUploadInitResponse(ClientBuildUploadInitResponseModel response
602615
var operation = request.SendWebRequest();
603616
while (!operation.isDone)
604617
{ }
618+
605619
if (operation.webRequest.IsConnectionError() || operation.webRequest.IsProtocolError())
606620
throw new ElympicsException($"Failed to upload file '{localFile}': {operation.webRequest.error}{Environment.NewLine}{operation.webRequest.downloadHandler.text}");
607621
}

Tests/Editor/TestGetValidFiles.cs

Lines changed: 132 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,132 @@
1+
using System.Linq;
2+
using NUnit.Framework;
3+
4+
namespace Elympics.Editor.Tests
5+
{
6+
public class TestGetValidFiles
7+
{
8+
private const string DefaultPrefix = "Build";
9+
10+
private static readonly string[] CompoundExtensions = ElympicsWebIntegration.compoundExtensions;
11+
private static readonly string[] InvalidFileNames = { "readme.txt", "notes.md", "config.yaml" };
12+
13+
private static string[] ValidFileNames =>
14+
CompoundExtensions.Select(ext => DefaultPrefix + ext).ToArray();
15+
16+
[Test]
17+
public void ReturnsEmpty_WhenNoFilesMatch()
18+
{
19+
var result = ElympicsWebIntegration.GetValidFiles(InvalidFileNames, CompoundExtensions);
20+
21+
Assert.IsEmpty(result);
22+
}
23+
24+
[Test]
25+
public void ReturnsEmpty_WhenInputIsEmpty()
26+
{
27+
var result = ElympicsWebIntegration.GetValidFiles(new string[0], CompoundExtensions);
28+
29+
Assert.IsEmpty(result);
30+
}
31+
32+
[Test]
33+
public void ParsesEachKnownExtension([ValueSource(nameof(CompoundExtensions))] string extension)
34+
{
35+
var fileName = DefaultPrefix + extension;
36+
var fileNames = new[] { fileName };
37+
38+
var result = ElympicsWebIntegration.GetValidFiles(fileNames, CompoundExtensions);
39+
40+
Assert.AreEqual(1, result.Count);
41+
Assert.AreEqual(DefaultPrefix, result[0].name);
42+
Assert.AreEqual(extension, result[0].extension);
43+
}
44+
45+
[Test]
46+
public void ParsesAllValidFilesTogether()
47+
{
48+
var result = ElympicsWebIntegration.GetValidFiles(ValidFileNames, CompoundExtensions);
49+
50+
Assert.AreEqual(CompoundExtensions.Length, result.Count);
51+
}
52+
53+
[Test]
54+
public void FiltersOutInvalidFiles()
55+
{
56+
var mixed = ValidFileNames.Concat(InvalidFileNames).ToArray();
57+
58+
var result = ElympicsWebIntegration.GetValidFiles(mixed, CompoundExtensions);
59+
60+
Assert.AreEqual(CompoundExtensions.Length, result.Count);
61+
foreach (var file in result)
62+
Assert.AreEqual(DefaultPrefix, file.name);
63+
}
64+
65+
[Test]
66+
public void ExtensionMatchingIsCaseInsensitive([ValueSource(nameof(CompoundExtensions))] string extension)
67+
{
68+
var fileName = DefaultPrefix + extension.ToUpperInvariant();
69+
var fileNames = new[] { fileName };
70+
71+
var result = ElympicsWebIntegration.GetValidFiles(fileNames, CompoundExtensions);
72+
73+
Assert.AreEqual(1, result.Count);
74+
}
75+
76+
[Test]
77+
public void UsesFirstDotSegmentAsName([ValueSource(nameof(CompoundExtensions))] string extension)
78+
{
79+
const string customPrefix = "MyGame";
80+
var fileName = customPrefix + extension;
81+
var fileNames = new[] { fileName };
82+
83+
var result = ElympicsWebIntegration.GetValidFiles(fileNames, CompoundExtensions);
84+
85+
Assert.AreEqual(1, result.Count);
86+
Assert.AreEqual(customPrefix, result[0].name);
87+
Assert.AreEqual(extension, result[0].extension);
88+
}
89+
90+
[Test]
91+
public void ParsesPrefixWithHyphenAndNumber([ValueSource(nameof(CompoundExtensions))] string extension)
92+
{
93+
const string prefixWithHyphen = "Build-1";
94+
var fileName = prefixWithHyphen + extension;
95+
var fileNames = new[] { fileName };
96+
97+
var result = ElympicsWebIntegration.GetValidFiles(fileNames, CompoundExtensions);
98+
99+
Assert.AreEqual(1, result.Count);
100+
Assert.AreEqual(prefixWithHyphen, result[0].name);
101+
Assert.AreEqual(extension, result[0].extension);
102+
}
103+
104+
[Test]
105+
public void ParsesPrefixWithDot([ValueSource(nameof(CompoundExtensions))] string extension)
106+
{
107+
const string prefixWithDot = "Build.1";
108+
var fileName = prefixWithDot + extension;
109+
var fileNames = new[] { fileName };
110+
111+
var result = ElympicsWebIntegration.GetValidFiles(fileNames, CompoundExtensions);
112+
113+
Assert.AreEqual(1, result.Count);
114+
Assert.AreEqual(prefixWithDot, result[0].name);
115+
Assert.AreEqual(extension, result[0].extension);
116+
}
117+
118+
[Test]
119+
public void ParseFilesWithBrotli([ValueSource(nameof(CompoundExtensions))] string extension)
120+
{
121+
const string packExtension = ".brotli";
122+
var fileName = DefaultPrefix + extension + packExtension;
123+
var fileNames = new[] { fileName };
124+
125+
var result = ElympicsWebIntegration.GetValidFiles(fileNames, CompoundExtensions);
126+
127+
Assert.AreEqual(1, result.Count);
128+
Assert.AreEqual(DefaultPrefix, result[0].name);
129+
Assert.AreEqual(extension + packExtension, result[0].extension);
130+
}
131+
}
132+
}

Tests/Editor/TestGetValidFiles.cs.meta

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

0 commit comments

Comments
 (0)