#if UNITY_2020_1_OR_NEWER using NUnit.Framework; using System; using System.Collections; using System.Collections.Generic; using System.IO; using System.Linq; using UnityEditor.AddressableAssets.Build; using UnityEditor.AddressableAssets.Build.DataBuilders; using UnityEditor.AddressableAssets.Settings; using UnityEditor.AddressableAssets.Settings.GroupSchemas; using UnityEditor.Build.Pipeline.Utilities; using UnityEditor.SceneManagement; using UnityEngine; using UnityEngine.AddressableAssets; using UnityEngine.AddressableAssets.ResourceLocators; using UnityEngine.ResourceManagement.AsyncOperations; using UnityEngine.ResourceManagement.ResourceProviders; using UnityEngine.ResourceManagement.Util; using UnityEngine.TestTools; namespace UnityEditor.AddressableAssets.Tests { public class AddressableAssetSettingsLocatorTests { AddressableAssetSettings m_Settings; const string TempPath = "TempGen"; string GetPath(string a) => $"Assets/{TempPath}/{a}"; EditorBuildSettingsScene[] m_PreviousScenes; [SetUp] public void Setup() { if (AssetDatabase.IsValidFolder($"Assets/{TempPath}")) { AssetDatabase.DeleteAsset($"Assets/{TempPath}"); AssetDatabase.Refresh(); } AssetDatabase.CreateFolder("Assets", "TempGen"); m_PreviousScenes = EditorBuildSettings.scenes; m_Settings = AddressableAssetSettings.Create(GetPath("Settings"), "AddressableAssetSettings.Tests", true, true); AssetDatabase.Refresh(); } [TearDown] public void Teardown() { AssetDatabase.Refresh(); // Many of the tests keep recreating assets in the same path, so we need to unload them completely so they don't get reused by the next test AssetDatabase.DeleteAsset(AssetDatabase.GetAssetPath(m_Settings)); Resources.UnloadAsset(m_Settings); if (AssetDatabase.IsValidFolder($"Assets/{TempPath}")) AssetDatabase.DeleteAsset($"Assets/{TempPath}"); EditorBuildSettings.scenes = m_PreviousScenes; AssetDatabase.Refresh(); } string CreateAsset(string assetName, string path) { AssetDatabase.CreateAsset(UnityEngine.AddressableAssets.Tests.TestObject.Create(assetName), path); AssetDatabase.SaveAssets(); AssetDatabase.ImportAsset(path, ImportAssetOptions.ForceSynchronousImport | ImportAssetOptions.ForceUpdate); AssetDatabase.Refresh(ImportAssetOptions.ForceUpdate); return AssetDatabase.AssetPathToGUID(path); } string CreateScene(string path) { var scene = EditorSceneManager.NewScene(NewSceneSetup.EmptyScene, NewSceneMode.Single); EditorSceneManager.SaveScene(scene, path); return AssetDatabase.AssetPathToGUID(path); } string CreateFolder(string folderName, string[] assetNames, HashSet guids = null) { var path = GetPath(folderName); Directory.CreateDirectory(path); foreach (var a in assetNames) { var guid = a.EndsWith(".unity", StringComparison.OrdinalIgnoreCase) ? CreateScene(Path.Combine(path, a)) : CreateAsset(a, Path.Combine(path, a)); guids?.Add(guid); } AssetDatabase.ImportAsset(path, ImportAssetOptions.ForceSynchronousImport | ImportAssetOptions.ForceUpdate); AssetDatabase.Refresh(ImportAssetOptions.ForceUpdate); return AssetDatabase.AssetPathToGUID(path); } void AssertLocateResult(IResourceLocator locator, object key, params string[] expectedInternalIds) { var type = typeof(T); Assert.IsTrue(locator.Locate(key, type, out var locations)); Assert.IsNotNull(locations); if (type != typeof(object)) { foreach (var l in locations) Assert.IsTrue(type.IsAssignableFrom(l.ResourceType)); } Assert.AreEqual(expectedInternalIds.Length, locations.Count); foreach (var e in expectedInternalIds) Assert.NotNull(locations.FirstOrDefault(s => s.InternalId == e), $"Locations do not contain entry with internal id of {e}"); } [UnityTest] public IEnumerator CanLoadAssetAsync_InEditMode() { var entry = m_Settings.CreateOrMoveEntry(CreateAsset("x", GetPath("x.asset")), m_Settings.DefaultGroup).address = "x"; Addressables.Instance.hasStartedInitialization = false; Addressables.Instance.InitializeAsync($"GUID:{AssetDatabase.AssetPathToGUID(m_Settings.AssetPath)}"); var op = Addressables.LoadAssetAsync("x"); while (!op.IsDone) yield return null; Assert.IsNotNull(op.Result); op.Release(); m_Settings.RemoveAssetEntry(entry); } [Test] public void CanLoadAssetSync_InEditMode() { var entry = m_Settings.CreateOrMoveEntry(CreateAsset("y", GetPath("y.asset")), m_Settings.DefaultGroup).address = "y"; Addressables.Instance.hasStartedInitialization = false; Addressables.Instance.InitializeAsync($"GUID:{AssetDatabase.AssetPathToGUID(m_Settings.AssetPath)}"); var op = Addressables.LoadAssetAsync("y"); op.WaitForCompletion(); Assert.IsNotNull(op.Result); op.Release(); m_Settings.RemoveAssetEntry(entry); } [Test] public void WhenLocatorWithSingleAsset_LocateWithAddress_ReturnsSingleLocation() { var path = GetPath("asset1.asset"); m_Settings.CreateOrMoveEntry(CreateAsset("asset1", path), m_Settings.DefaultGroup).address = "address1"; AssertLocateResult(new AddressableAssetSettingsLocator(m_Settings), "address1", path); } [Test] public void WhenLocatorWithSingleMonoscript_LocateReturnsSingleLocation() { string id = "mono"; var path = GetPath("mono.asset"); AssetDatabase.CreateAsset(UnityEngine.AddressableAssets.Tests.TestObjectWithSerializableField.Create(id), path); AssetDatabase.SaveAssets(); AssetDatabase.ImportAsset(path, ImportAssetOptions.ForceSynchronousImport | ImportAssetOptions.ForceUpdate); AssetDatabase.Refresh(ImportAssetOptions.ForceUpdate); m_Settings.CreateOrMoveEntry(AssetDatabase.AssetPathToGUID(path), m_Settings.DefaultGroup).address = id; var locator = new AddressableAssetSettingsLocator(m_Settings); Assert.IsTrue(locator.Locate(id, null, out var locs)); Assert.IsNotNull(locs); Assert.AreEqual(1, locs.Count); Assert.AreEqual(path, locs[0].InternalId, $"Locations do not contain entry with internal id of {path}"); } [Test] public void WhenLocatorWithSingleAsset_LocateWithSameAddressAsLabel_ReturnsSingleLocation() { var path = GetPath("asset1.asset"); var e = m_Settings.CreateOrMoveEntry(CreateAsset("asset1", path), m_Settings.DefaultGroup); e.address = "address1"; e.SetLabel("address1", true, true); AssertLocateResult(new AddressableAssetSettingsLocator(m_Settings), "address1", path); } [Test] public void WhenLocatorWithSingleAsset_LocateWithInvalidKeyReturnsFalse() { m_Settings.CreateOrMoveEntry(CreateAsset("asset1", GetPath("asset1.asset")), m_Settings.DefaultGroup).address = "address1"; var locator = new AddressableAssetSettingsLocator(m_Settings); Assert.IsFalse(locator.Locate("invalid", null, out var locs)); Assert.IsNull(locs); } [Test] public void WhenLocatorWithSingleAsset_LocateWithGuidReturnsSingleLocation() { var guid = CreateAsset("asset1", GetPath("asset1.asset")); m_Settings.CreateOrMoveEntry(guid, m_Settings.DefaultGroup).address = "address1"; AssertLocateResult(new AddressableAssetSettingsLocator(m_Settings), guid, GetPath("asset1.asset")); } [Test] public void WhenLocatorWithMultipeAssets_LocateWithAddressReturnsSingleLocation() { m_Settings.CreateOrMoveEntry(CreateAsset("asset1", GetPath("asset1.asset")), m_Settings.DefaultGroup).address = "address1"; m_Settings.CreateOrMoveEntry(CreateAsset("asset2", GetPath("asset2.asset")), m_Settings.DefaultGroup).address = "address2"; AssertLocateResult(new AddressableAssetSettingsLocator(m_Settings), "address1", GetPath("asset1.asset")); } [Test] public void WhenLocatorWithMultipeAssets_LocateWithSharedAddressReturnsMultipleLocations() { m_Settings.CreateOrMoveEntry(CreateAsset("asset1", GetPath("asset1.asset")), m_Settings.DefaultGroup).address = "address1"; m_Settings.CreateOrMoveEntry(CreateAsset("asset2", GetPath("asset2.asset")), m_Settings.DefaultGroup).address = "address1"; AssertLocateResult(new AddressableAssetSettingsLocator(m_Settings), "address1", GetPath("asset1.asset"), GetPath("asset2.asset")); } [Test] public void WhenLocatorWithMultipeAssets_LocateWithSharedLabelReturnsMultipleLocations() { m_Settings.CreateOrMoveEntry(CreateAsset("asset1", GetPath("asset1.asset")), m_Settings.DefaultGroup).SetLabel("label", true, true); m_Settings.CreateOrMoveEntry(CreateAsset("asset2", GetPath("asset2.asset")), m_Settings.DefaultGroup).SetLabel("label", true, true); AssertLocateResult(new AddressableAssetSettingsLocator(m_Settings), "label", GetPath("asset1.asset"), GetPath("asset2.asset")); } [Test] public void WhenLocatorWithAssetsThatMatchAssetsInFolderAndResources_LocateAllMatches() { CreateFolder("Resources/TestFolder", new string[] {"asset1.asset"}); var folderGUID = CreateFolder("TestFolder", new string[] {"asset1.asset"}); m_Settings.CreateOrMoveEntry(folderGUID, m_Settings.DefaultGroup).address = "TestFolder"; var assetGUID = CreateAsset("asset1", GetPath("asset1.asset")); m_Settings.CreateOrMoveEntry(assetGUID, m_Settings.DefaultGroup).address = "TestFolder/asset1.asset"; AssertLocateResult(new AddressableAssetSettingsLocator(m_Settings), "TestFolder/asset1.asset", "TestFolder/asset1", GetPath("TestFolder/asset1.asset"), GetPath("asset1.asset") ); } [Test] public void WhenLocatorWithAssetsInMarkedFolder_LocateWithAssetReferenceSucceeds() { CreateFolder("TestFolder1/TestFolder2", new string[] {"asset1.asset", "asset2.asset", "asset3.asset"}); var folderGUID = AssetDatabase.AssetPathToGUID(GetPath("TestFolder1")); m_Settings.CreateOrMoveEntry(folderGUID, m_Settings.DefaultGroup).address = "TF1"; var assetRef = m_Settings.CreateAssetReference(AssetDatabase.AssetPathToGUID(GetPath("TestFolder1/TestFolder2/asset1.asset"))); AssertLocateResult(new AddressableAssetSettingsLocator(m_Settings), assetRef.RuntimeKey, GetPath("TestFolder1/TestFolder2/asset1.asset")); } [Test] public void WhenLocatorWithAssetsInFolder_LocateWithAssetKeySucceeds() { var folderGUID = CreateFolder("TestFolder", new string[] {"asset1.asset", "asset2.asset", "asset3.asset"}); m_Settings.CreateOrMoveEntry(folderGUID, m_Settings.DefaultGroup).address = "TF"; AssertLocateResult(new AddressableAssetSettingsLocator(m_Settings), "TF/asset1.asset", GetPath("TestFolder/asset1.asset")); } [Test] public void WhenLocatorWithAssetsInMatchingFolders_LocateWithAssetKeySucceeds() { var folderGUID1 = CreateFolder("TestFolder1", new string[] {"asset1_1.asset", "asset2_1.asset", "asset3_1.asset"}); var folderGUID2 = CreateFolder("TestFolder2", new string[] {"asset1_2.asset", "asset2_2.asset", "asset3_2.asset"}); m_Settings.CreateOrMoveEntry(folderGUID1, m_Settings.DefaultGroup).address = "TF"; m_Settings.CreateOrMoveEntry(folderGUID2, m_Settings.DefaultGroup).address = "TF"; AssertLocateResult(new AddressableAssetSettingsLocator(m_Settings), "TF/asset1_1.asset", GetPath("TestFolder1/asset1_1.asset")); AssertLocateResult(new AddressableAssetSettingsLocator(m_Settings), "TF/asset1_2.asset", GetPath("TestFolder2/asset1_2.asset")); } [Test] public void WhenLocatorWithAssetsInMatchingFolderAndAssets_LocateWithAssetKeySucceeds() { var folderGUID1 = CreateFolder("TestFolder1", new string[] {"asset1.asset", "asset2.asset", "asset3.asset"}); var folderGUID2 = CreateFolder("TestFolder2", new string[] {"asset1.asset", "asset2.asset", "asset3.asset"}); m_Settings.CreateOrMoveEntry(folderGUID1, m_Settings.DefaultGroup).address = "TF"; m_Settings.CreateOrMoveEntry(folderGUID2, m_Settings.DefaultGroup).address = "TF"; AssertLocateResult(new AddressableAssetSettingsLocator(m_Settings), "TF/asset1.asset", GetPath("TestFolder1/asset1.asset"), GetPath("TestFolder2/asset1.asset")); } [Test] public void WhenLocatorWithAssetAndFolderNameMatch_LocateWithAssetKeySucceeds() { var folderGUID = CreateFolder("TestName", new string[] {"TestName.asset"}); m_Settings.CreateOrMoveEntry(folderGUID, m_Settings.DefaultGroup).address = "TF"; AssertLocateResult(new AddressableAssetSettingsLocator(m_Settings), "TF/TestName.asset", GetPath("TestName/TestName.asset")); } [Test] public void WhenLocatorWithAssetAndFolderAddrMatch_LocateWithAssetKeySucceeds() { var folderGUID = CreateFolder("TestName", new string[] {"TF.asset"}); m_Settings.CreateOrMoveEntry(folderGUID, m_Settings.DefaultGroup).address = "TF"; AssertLocateResult(new AddressableAssetSettingsLocator(m_Settings), "TF/TF.asset", GetPath("TestName/TF.asset")); } [Test] public void WhenLocatorWithAssetsInFolder_LocateWithFolderKeyFails() { var folderGUID = CreateFolder("TestFolder", new string[] {"asset1.asset", "asset2.asset", "asset3.asset"}); m_Settings.CreateOrMoveEntry(folderGUID, m_Settings.DefaultGroup).address = "TF"; var locator = new AddressableAssetSettingsLocator(m_Settings); Assert.IsFalse(locator.Locate("TF", null, out var locations)); } [Test] public void WhenLocatorWithAssetsInFolder_LocateWithFolderLabelSucceeds() { var folderGUID = CreateFolder("TestFolder", new string[] {"asset1.asset", "asset2.asset", "asset3.asset"}); var folderEntry = m_Settings.CreateOrMoveEntry(folderGUID, m_Settings.DefaultGroup); folderEntry.address = "TF"; folderEntry.SetLabel("FolderLabel", true, true, true); AssertLocateResult(new AddressableAssetSettingsLocator(m_Settings), "FolderLabel", GetPath("TestFolder/asset1.asset"), GetPath("TestFolder/asset2.asset"), GetPath("TestFolder/asset3.asset")); } [Test] public void WhenLocatorWithAssetsInFolderWithSimilarNames_LocateWithAssetKeySucceeds() { var folderGUID = CreateFolder("TestFolder", new string[] {"asset1.asset", "asset.asset", "asset1_more.asset"}); m_Settings.CreateOrMoveEntry(folderGUID, m_Settings.DefaultGroup).address = "TF"; AssertLocateResult(new AddressableAssetSettingsLocator(m_Settings), "TF/asset1.asset", GetPath("TestFolder/asset1.asset")); } [Test] public void WhenLocatorWithAssetsInNestedFolders_LocateWithAssetKeySucceeds() { var folderGUID1 = CreateFolder("TestFolder", new string[] {"asset1.asset", "asset2.asset", "asset3.asset"}); var folderGUID2 = CreateFolder("TestFolder/TestSubFolder1", new string[] {"asset1.asset", "asset2.asset", "asset3.asset"}); var folderGUID3 = CreateFolder("TestFolder/TestSubFolder1/TestSubFolder2", new string[] {"asset1.asset", "asset2.asset", "asset3.asset"}); m_Settings.CreateOrMoveEntry(folderGUID1, m_Settings.DefaultGroup).address = "TF"; var locator = new AddressableAssetSettingsLocator(m_Settings); AssertLocateResult(locator, "TF/asset1.asset", GetPath("TestFolder/asset1.asset")); AssertLocateResult(locator, "TF/TestSubFolder1/asset1.asset", GetPath("TestFolder/TestSubFolder1/asset1.asset")); AssertLocateResult(locator, "TF/TestSubFolder1/TestSubFolder2/asset1.asset", GetPath("TestFolder/TestSubFolder1/TestSubFolder2/asset1.asset")); } [Test] public void WhenLocatorWithAssetsInNestedFoldersThatAreBothAddressable_LocateWithAssetKeySucceeds() { var folderGUID1 = CreateFolder("TestFolder", new string[] {"asset1.asset", "asset2.asset", "asset3.asset"}); var folderGUID2 = CreateFolder("TestFolder/TestSubFolder1", new string[] {"asset1.asset", "asset2.asset", "asset3.asset"}); var folderGUID3 = CreateFolder("TestFolder/TestSubFolder1/TestSubFolder2", new string[] {"asset1.asset", "asset2.asset", "asset3.asset"}); m_Settings.CreateOrMoveEntry(folderGUID1, m_Settings.DefaultGroup).address = "TF"; m_Settings.CreateOrMoveEntry(folderGUID2, m_Settings.DefaultGroup).address = "TF2"; var locator = new AddressableAssetSettingsLocator(m_Settings); AssertLocateResult(locator, "TF/asset1.asset", GetPath("TestFolder/asset1.asset")); AssertLocateResult(locator, "TF2/asset1.asset", GetPath("TestFolder/TestSubFolder1/asset1.asset")); AssertLocateResult(locator, "TF2/TestSubFolder2/asset1.asset", GetPath("TestFolder/TestSubFolder1/TestSubFolder2/asset1.asset")); } void CreateAndAddScenesToEditorBuildSettings(string scenePrefix, int count, HashSet guids = null) { var sceneList = new List(); for (int i = 0; i < count; i++) { var path = GetPath($"{scenePrefix}{i}.unity"); var scene = EditorSceneManager.NewScene(NewSceneSetup.DefaultGameObjects, i == 0 ? NewSceneMode.Single : NewSceneMode.Additive); EditorSceneManager.SaveScene(scene, path); var guid = AssetDatabase.AssetPathToGUID(path); guids?.Add(guid); sceneList.Add(new EditorBuildSettingsScene(path, true)); } EditorBuildSettings.scenes = sceneList.ToArray(); } [Test] public void WhenLocatorWithScenesInSceneList_LocateWithSceneIndexKeyReturnsLocationForScene() { CreateAndAddScenesToEditorBuildSettings("testScene", 3); var locator = new AddressableAssetSettingsLocator(m_Settings); for (int i = 0; i < 3; i++) AssertLocateResult(locator, i, GetPath($"testScene{i}.unity")); } [Test] public void WhenLocatorWithScenesInSceneList_LocateWithSceneGUIDKeyReturnsLocationForScene() { CreateAndAddScenesToEditorBuildSettings("testScene", 3); var locator = new AddressableAssetSettingsLocator(m_Settings); for (int i = 0; i < EditorBuildSettings.scenes.Length; i++) AssertLocateResult(locator, EditorBuildSettings.scenes[i].guid.ToString(), GetPath($"testScene{i}.unity")); } [Test] public void WhenLocatorWithScenesInSceneList_LocateWithSceneNameKeyReturnsLocationForScene() { CreateAndAddScenesToEditorBuildSettings("testScene", 3); var locator = new AddressableAssetSettingsLocator(m_Settings); for (int i = 0; i < EditorBuildSettings.scenes.Length; i++) AssertLocateResult(locator, $"testScene{i}", GetPath($"testScene{i}.unity")); } [Test] public void LocateWithSceneInstanceType_DoesNotReturnNonSceneLocations() { CreateAndAddScenesToEditorBuildSettings("test", 1); var guid = CreateAsset("test0", GetPath("asset1.asset")); m_Settings.CreateOrMoveEntry(guid, m_Settings.DefaultGroup).address = "test0"; var locator = new AddressableAssetSettingsLocator(m_Settings); Assert.IsTrue(locator.Locate("test0", typeof(SceneInstance), out var locations)); Assert.AreEqual(1, locations.Count); Assert.AreEqual(typeof(SceneInstance), locations[0].ResourceType); } [Test] public void LocateWithSceneInstanceType_ReturnsLocationsWhenTypeNull() { CreateAndAddScenesToEditorBuildSettings("test", 1); var guid = CreateAsset("test0", GetPath("asset1.asset")); m_Settings.CreateOrMoveEntry(guid, m_Settings.DefaultGroup).address = "test0"; var locator = new AddressableAssetSettingsLocator(m_Settings); Assert.IsTrue(locator.Locate("test0", null, out var locations)); Assert.AreEqual(2, locations.Count); Assert.AreEqual(typeof(SceneInstance), locations[0].ResourceType); } [Test] public void LocateWithNonSceneInstanceType_DoesNotReturnSceneLocations() { CreateAndAddScenesToEditorBuildSettings("test", 1); var guid = CreateAsset("test0", GetPath("asset1.asset")); m_Settings.CreateOrMoveEntry(guid, m_Settings.DefaultGroup).address = "test0"; var locator = new AddressableAssetSettingsLocator(m_Settings); Assert.IsTrue(locator.Locate("test0", typeof(UnityEngine.AddressableAssets.Tests.TestObject), out var locations)); Assert.AreEqual(1, locations.Count); Assert.AreEqual(typeof(UnityEngine.AddressableAssets.Tests.TestObject), locations[0].ResourceType); } [Test] public void WhenLocatorWithScenesInSceneList_LocateWithISceneInstanceType_ReturnsLocationForScene() { CreateAndAddScenesToEditorBuildSettings("testScene", 3); var locator = new AddressableAssetSettingsLocator(m_Settings); for (int i = 0; i < EditorBuildSettings.scenes.Length; i++) AssertLocateResult(locator, $"testScene{i}", GetPath($"testScene{i}.unity")); } public void RunResourcesTestWithAsset(bool IncludeResourcesFolders) { int builtInResourceCount = ResourcesTestUtility.GetResourcesEntryCount(m_Settings, true); var path = GetPath("Resources/test.asset"); var dir = Path.GetDirectoryName(path); Directory.CreateDirectory(dir); AssetDatabase.CreateAsset(UnityEngine.AddressableAssets.Tests.TestObject.Create("test"), path); AssetDatabase.SaveAssets(); m_Settings.FindGroup(g => g.HasSchema()).GetSchema().IncludeResourcesFolders = IncludeResourcesFolders; var locator = new AddressableAssetSettingsLocator(m_Settings); var res = locator.Locate("test", null, out var locations); Assert.AreEqual(res, IncludeResourcesFolders); if (IncludeResourcesFolders) Assert.AreEqual(1 + builtInResourceCount, locations.Count + builtInResourceCount); else Assert.IsNull(locations); AssetDatabase.DeleteAsset(path); Directory.Delete(dir); } [Test] public void WhenAGroupHasIncludeResourcesFoldersEnabled_LocateFindsAssetInResourcesFolder() { RunResourcesTestWithAsset(true); } [Test] public void WhenAGroupHasIncludeResourcesFoldersDisabled_LocateFailesForAssetInResourcesFolder() { RunResourcesTestWithAsset(false); } static HashSet ExpectedKeys = new HashSet(new object[] { "TestScene0", //scene name in build settings 0, //index if TestScene0 "TestScene1", 1, "TestScene2", 2, //assets in a folder with an address "AssetAddress", "AssetLabel", "TF/asset2.asset", "TF/asset3.asset", //scenes in a folder "TF/TestSubFolder2/scene1.unity", "TF/TestSubFolder2/scene2.unity", "TF/TestSubFolder2/scene3.unity", //label applied to folder "FolderLabel1", //assets in subfolder without address "TestFolder/TestSubFolder1/asset1.asset", "TestFolder/TestSubFolder1/asset2.asset", "TestFolder/TestSubFolder1/asset3.asset", //assets in resource in subfolder with address "TestFolder/TestSubFolder1/Resources/asset1.asset", "TestFolder/TestSubFolder1/Resources/asset2.asset", "TestFolder/TestSubFolder1/Resources/asset3.asset", //resources keys "asset1", "asset2", "asset3", }); void SetupLocatorAssets() { var folderGUID1 = CreateFolder("TestFolder", new string[] {"asset1.asset", "asset2.asset", "asset3.asset"}, ExpectedKeys); var folderGUID2 = CreateFolder("TestFolder/TestSubFolder1", new string[] {"asset1.asset", "asset2.asset", "asset3.asset"}, ExpectedKeys); var folderGUID3 = CreateFolder("TestFolder/TestSubFolder1/Resources", new string[] {"asset1.asset", "asset2.asset", "asset3.asset"}, ExpectedKeys); var folderGUID4 = CreateFolder("TestFolder/TestSubFolder2", new string[] {"scene1.unity", "scene2.unity", "scene3.unity"}, ExpectedKeys); CreateAndAddScenesToEditorBuildSettings("TestScene", 3, ExpectedKeys); var assetInFolder = m_Settings.CreateOrMoveEntry( AssetDatabase.AssetPathToGUID(GetPath("TestFolder/asset1.asset")), m_Settings.DefaultGroup); assetInFolder.address = "AssetAddress"; assetInFolder.SetLabel("AssetLabel", true, true, true); var tf = m_Settings.CreateOrMoveEntry(folderGUID1, m_Settings.DefaultGroup); tf.address = "TF"; tf.SetLabel("FolderLabel1", true, true, true); var tf2 = m_Settings.CreateOrMoveEntry(folderGUID2, m_Settings.DefaultGroup); tf2.address = "TestFolder/TestSubFolder1"; } [UnityTest] public IEnumerator Locator_KeysProperty_Contains_Expected_Keys_ForAllBuildScripts() { using (new HideResourceFoldersScope()) { SetupLocatorAssets(); AddressablesDataBuilderInput input = new AddressablesDataBuilderInput(m_Settings); input.Logger = new BuildLog(); var fastMode = ScriptableObject.CreateInstance(); var virtualMode = ScriptableObject.CreateInstance(); var packedMode = ScriptableObject.CreateInstance(); var packedPlayMode = ScriptableObject.CreateInstance(); AddressablesImpl fastModeImpl = new AddressablesImpl(new DefaultAllocationStrategy()); fastModeImpl.AddResourceLocator(new AddressableAssetSettingsLocator(m_Settings)); var fastModeSettingsPath = fastMode.BuildData(input).OutputPath; var virtualModeSettingsPath = virtualMode.BuildData(input).OutputPath; var packedModeSettingsPath = packedMode.BuildData(input).OutputPath; var packedPlayModeSettingsPath = packedPlayMode.BuildData(input).OutputPath; AddressablesImpl fmImpl = new AddressablesImpl(new DefaultAllocationStrategy()); AddressablesImpl virtualImpl = new AddressablesImpl(new DefaultAllocationStrategy()); AddressablesImpl packedImpl = new AddressablesImpl(new DefaultAllocationStrategy()); AddressablesImpl packedPlayImpl = new AddressablesImpl(new DefaultAllocationStrategy()); fmImpl.AddResourceLocator(new AddressableAssetSettingsLocator(m_Settings)); virtualImpl.AddResourceLocator(new AddressableAssetSettingsLocator(m_Settings)); packedImpl.AddResourceLocator(new AddressableAssetSettingsLocator(m_Settings)); packedPlayImpl.AddResourceLocator(new AddressableAssetSettingsLocator(m_Settings)); var fastModeHandle = fmImpl.ResourceManager.StartOperation(new FastModeInitializationOperation(fmImpl, m_Settings), default(AsyncOperationHandle)); var virtualHandle = virtualImpl.InitializeAsync(virtualModeSettingsPath); var packedHandle = packedImpl.InitializeAsync(packedModeSettingsPath); var packedPlayHandle = packedPlayImpl.InitializeAsync(packedPlayModeSettingsPath); while (!fastModeHandle.IsDone && !virtualHandle.IsDone && !packedHandle.IsDone && !packedPlayHandle.IsDone) yield return null; var fastModeKeys = fmImpl.ResourceLocators.First(l => l.GetType() == typeof(AddressableAssetSettingsLocator)).Keys; var virtualModeKeys = virtualImpl.ResourceLocators.First(l => l.GetType() == typeof(AddressableAssetSettingsLocator)).Keys; var packedModeKeys = packedImpl.ResourceLocators.First(l => l.GetType() == typeof(AddressableAssetSettingsLocator)).Keys; var packedPlayKeys = packedPlayImpl.ResourceLocators.First(l => l.GetType() == typeof(AddressableAssetSettingsLocator)).Keys; var builtInPackageResourcesEntries = ResourcesTestUtility.GetResourcesEntries(m_Settings, true); foreach (var key in builtInPackageResourcesEntries) { ExpectedKeys.Add(key.guid); ExpectedKeys.Add(key.address); } //Get our baseline Assert.AreEqual(ExpectedKeys.Count, fastModeKeys.Count()); foreach (var key in fastModeKeys) Assert.IsTrue(ExpectedKeys.Contains(key)); //Transitive property to check other build scripts CollectionAssert.AreEqual(fastModeKeys, virtualModeKeys); CollectionAssert.AreEqual(fastModeKeys, packedPlayKeys); CollectionAssert.AreEqual(fastModeKeys, packedModeKeys); } } [Test] public void Locator_KeysProperty_Contains_Expected_Keys() { using (new HideResourceFoldersScope()) { SetupLocatorAssets(); var locator = new AddressableAssetSettingsLocator(m_Settings); if (ExpectedKeys.Count != locator.Keys.Count()) { Debug.Log("GENERATED"); int i = 0; foreach (var k in locator.Keys) { Debug.Log($"[{i}] {k}"); i++; } Debug.Log("EXPECTED"); i = 0; foreach (var k in ExpectedKeys) { Debug.Log($"[{i}] {k}"); i++; } } var builtInPackageResourcesEntries = ResourcesTestUtility.GetResourcesEntries(m_Settings, true); foreach (var key in builtInPackageResourcesEntries) { ExpectedKeys.Add(key.guid); ExpectedKeys.Add(key.address); } Assert.AreEqual(ExpectedKeys.Count, locator.Keys.Count()); int index = 0; foreach (var k in locator.Keys) { Assert.IsTrue(ExpectedKeys.Contains(k), $"Cannot find key {k}, index={index} in expected keys"); index++; } } } } } #endif