using UnityEngine;
using UnityEngine.AddressableAssets;
using UnityEngine.ResourceManagement.AsyncOperations;
namespace DanroJump.Settings
{
///
/// Загружает базу сервисных настроек из прямой ссылки или через Addressables.
///
public sealed class AddressableServiceSettingsDatabaseProvider : IServiceSettingsDatabaseProvider
{
private readonly string address;
private readonly ServiceSettingsDatabase fallbackDatabase;
private AsyncOperationHandle? loadedHandle;
///
/// Создает provider для addressable-базы настроек.
///
public AddressableServiceSettingsDatabaseProvider(
string address,
ServiceSettingsDatabase fallbackDatabase = null)
{
this.address = address;
this.fallbackDatabase = fallbackDatabase;
}
///
/// Возвращает прямую fallback-базу без блокировки Addressables или загружает базу по адресу.
///
public ServiceSettingsDatabase Load()
{
ReleaseLoadedHandle();
if (fallbackDatabase != null)
{
return fallbackDatabase;
}
if (string.IsNullOrWhiteSpace(address))
{
return null;
}
try
{
var handle = Addressables.LoadAssetAsync(address);
var database = handle.WaitForCompletion();
// Удерживаем handle только для успешно загруженного addressable-asset.
if (handle.Status == AsyncOperationStatus.Succeeded && database != null)
{
loadedHandle = handle;
return database;
}
if (handle.IsValid())
{
Addressables.Release(handle);
}
Debug.LogWarning(
$"[{nameof(AddressableServiceSettingsDatabaseProvider)}] Failed to load settings database at address '{address}'. Fallback will be used.");
}
catch (System.Exception exception)
{
Debug.LogWarning(
$"[{nameof(AddressableServiceSettingsDatabaseProvider)}] Failed to load settings database at address '{address}': {exception.Message}");
}
return null;
}
///
/// Освобождает addressable-handle, если база была загружена через Addressables.
///
public void Dispose()
{
ReleaseLoadedHandle();
}
private void ReleaseLoadedHandle()
{
if (loadedHandle.HasValue && loadedHandle.Value.IsValid())
{
Addressables.Release(loadedHandle.Value);
}
loadedHandle = null;
}
}
}