Connect up the new asset cache and introduce an asynchronous call path
for asset retrieval (full asset only) to ease migration to the new system0.6.5-rc1
parent
d8e1842d25
commit
1a910b6e1d
|
@ -529,5 +529,11 @@ namespace OpenSim.Framework
|
|||
m_Lookup.Remove(uuid);
|
||||
m_Index.Remove(item);
|
||||
}
|
||||
|
||||
public void Clear()
|
||||
{
|
||||
m_Index.Clear();
|
||||
m_Lookup.Clear();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -45,6 +45,9 @@ namespace OpenSim.Region.CoreModules.Asset
|
|||
MethodBase.GetCurrentMethod().DeclaringType);
|
||||
|
||||
private bool m_Enabled = false;
|
||||
private Cache m_Cache = new Cache(CacheMedium.Memory,
|
||||
CacheStrategy.Aggressive,
|
||||
CacheFlags.AllowUpdate);
|
||||
|
||||
public string Name
|
||||
{
|
||||
|
@ -69,6 +72,8 @@ namespace OpenSim.Region.CoreModules.Asset
|
|||
m_Enabled = true;
|
||||
|
||||
m_log.Info("[ASSET CACHE]: Core asset cache enabled");
|
||||
|
||||
m_Cache.Size = 32768;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -99,19 +104,22 @@ namespace OpenSim.Region.CoreModules.Asset
|
|||
|
||||
public void Cache(AssetBase asset)
|
||||
{
|
||||
m_Cache.Store(asset.ID, asset);
|
||||
}
|
||||
|
||||
public AssetBase Get(string id)
|
||||
{
|
||||
return null;
|
||||
return (AssetBase)m_Cache.Get(id);
|
||||
}
|
||||
|
||||
public void Expire(string id)
|
||||
{
|
||||
m_Cache.Invalidate(id);
|
||||
}
|
||||
|
||||
public void Clear()
|
||||
{
|
||||
m_Cache.Clear();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -30,6 +30,7 @@ using Nini.Config;
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Reflection;
|
||||
using OpenSim.Framework;
|
||||
using OpenSim.Servers.Base;
|
||||
using OpenSim.Region.Framework.Interfaces;
|
||||
using OpenSim.Region.Framework.Scenes;
|
||||
|
@ -37,14 +38,14 @@ using OpenSim.Services.Interfaces;
|
|||
|
||||
namespace OpenSim.Region.CoreModules.ServiceConnectors.Asset
|
||||
{
|
||||
public class LocalAssetServicesConnector : ISharedRegionModule
|
||||
public class LocalAssetServicesConnector :
|
||||
ISharedRegionModule, IAssetService
|
||||
{
|
||||
private static readonly ILog m_log =
|
||||
LogManager.GetLogger(
|
||||
MethodBase.GetCurrentMethod().DeclaringType);
|
||||
|
||||
private Dictionary<Scene, IImprovedAssetCache> m_AssetCache =
|
||||
new Dictionary<Scene, IImprovedAssetCache>();
|
||||
private IImprovedAssetCache m_Cache = null;
|
||||
|
||||
private IAssetService m_AssetService;
|
||||
|
||||
|
@ -108,15 +109,11 @@ namespace OpenSim.Region.CoreModules.ServiceConnectors.Asset
|
|||
if (!m_Enabled)
|
||||
return;
|
||||
|
||||
scene.RegisterModuleInterface<IAssetService>(m_AssetService);
|
||||
scene.RegisterModuleInterface<IAssetService>(this);
|
||||
}
|
||||
|
||||
public void RemoveRegion(Scene scene)
|
||||
{
|
||||
if (!m_Enabled)
|
||||
return;
|
||||
|
||||
m_AssetCache.Remove(scene);
|
||||
}
|
||||
|
||||
public void RegionLoaded(Scene scene)
|
||||
|
@ -124,18 +121,113 @@ namespace OpenSim.Region.CoreModules.ServiceConnectors.Asset
|
|||
if (!m_Enabled)
|
||||
return;
|
||||
|
||||
m_AssetCache[scene] =
|
||||
scene.RequestModuleInterface<IImprovedAssetCache>();
|
||||
if (m_Cache == null)
|
||||
{
|
||||
m_Cache = scene.RequestModuleInterface<IImprovedAssetCache>();
|
||||
|
||||
if (!(m_Cache is ISharedRegionModule))
|
||||
m_Cache = null;
|
||||
}
|
||||
|
||||
m_log.InfoFormat("[ASSET CONNECTOR]: Enabled local assets for region {0}", scene.RegionInfo.RegionName);
|
||||
|
||||
m_AssetCache[scene] =
|
||||
scene.RequestModuleInterface<IImprovedAssetCache>();
|
||||
|
||||
if (m_AssetCache[scene] != null)
|
||||
if (m_Cache != null)
|
||||
{
|
||||
m_log.InfoFormat("[ASSET CONNECTOR]: Enabled asset caching for region {0}", scene.RegionInfo.RegionName);
|
||||
}
|
||||
else
|
||||
{
|
||||
// Short-circuit directly to storage layer
|
||||
//
|
||||
scene.UnregisterModuleInterface<IAssetService>(this);
|
||||
scene.RegisterModuleInterface<IAssetService>(m_AssetService);
|
||||
}
|
||||
}
|
||||
|
||||
public AssetBase Get(string id)
|
||||
{
|
||||
AssetBase asset = m_Cache.Get(id);
|
||||
|
||||
if (asset == null)
|
||||
return m_AssetService.Get(id);
|
||||
return asset;
|
||||
}
|
||||
|
||||
public AssetMetadata GetMetadata(string id)
|
||||
{
|
||||
AssetBase asset = m_Cache.Get(id);
|
||||
|
||||
if (asset != null)
|
||||
return asset.Metadata;
|
||||
|
||||
asset = m_AssetService.Get(id);
|
||||
if (asset != null)
|
||||
{
|
||||
m_Cache.Cache(asset);
|
||||
return asset.Metadata;
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
public byte[] GetData(string id)
|
||||
{
|
||||
AssetBase asset = m_Cache.Get(id);
|
||||
|
||||
if (asset != null)
|
||||
return asset.Data;
|
||||
|
||||
asset = m_AssetService.Get(id);
|
||||
if (asset != null)
|
||||
{
|
||||
m_Cache.Cache(asset);
|
||||
return asset.Data;
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
public bool Get(string id, Object sender, AssetRetrieved handler)
|
||||
{
|
||||
AssetBase asset = m_Cache.Get(id);
|
||||
|
||||
if (asset != null)
|
||||
{
|
||||
handler(id, sender, asset);
|
||||
return true;
|
||||
}
|
||||
|
||||
return m_AssetService.Get(id, sender, delegate (string assetID, Object s, AssetBase a)
|
||||
{
|
||||
if (a != null)
|
||||
m_Cache.Cache(a);
|
||||
handler(assetID, s, a);
|
||||
});
|
||||
}
|
||||
|
||||
public string Store(AssetBase asset)
|
||||
{
|
||||
m_Cache.Cache(asset);
|
||||
return m_AssetService.Store(asset);
|
||||
}
|
||||
|
||||
public bool UpdateContent(string id, byte[] data)
|
||||
{
|
||||
AssetBase asset = m_Cache.Get(id);
|
||||
if (asset != null)
|
||||
{
|
||||
asset.Data = data;
|
||||
m_Cache.Cache(asset);
|
||||
}
|
||||
|
||||
return m_AssetService.UpdateContent(id, data);
|
||||
}
|
||||
|
||||
public bool Delete(string id)
|
||||
{
|
||||
m_Cache.Expire(id);
|
||||
|
||||
return m_AssetService.Delete(id);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -49,8 +49,7 @@ namespace OpenSim.Region.CoreModules.ServiceConnectors.Asset
|
|||
|
||||
private bool m_Enabled = false;
|
||||
private string m_ServerURI = String.Empty;
|
||||
private Dictionary<Scene, IImprovedAssetCache> m_AssetCache =
|
||||
new Dictionary<Scene, IImprovedAssetCache>();
|
||||
private IImprovedAssetCache m_Cache = null;
|
||||
|
||||
public string Name
|
||||
{
|
||||
|
@ -106,10 +105,6 @@ namespace OpenSim.Region.CoreModules.ServiceConnectors.Asset
|
|||
|
||||
public void RemoveRegion(Scene scene)
|
||||
{
|
||||
if (!m_Enabled)
|
||||
return;
|
||||
|
||||
m_AssetCache.Remove(scene);
|
||||
}
|
||||
|
||||
public void RegionLoaded(Scene scene)
|
||||
|
@ -117,12 +112,20 @@ namespace OpenSim.Region.CoreModules.ServiceConnectors.Asset
|
|||
if (!m_Enabled)
|
||||
return;
|
||||
|
||||
m_AssetCache[scene] =
|
||||
scene.RequestModuleInterface<IImprovedAssetCache>();
|
||||
if (m_Cache == null)
|
||||
{
|
||||
m_Cache = scene.RequestModuleInterface<IImprovedAssetCache>();
|
||||
|
||||
// Since we are a shared module and scene data is not
|
||||
// available for every method, the cache must be shared, too
|
||||
//
|
||||
if (!(m_Cache is ISharedRegionModule))
|
||||
m_Cache = null;
|
||||
}
|
||||
|
||||
m_log.InfoFormat("[ASSET CONNECTOR]: Enabled remote assets for region {0}", scene.RegionInfo.RegionName);
|
||||
|
||||
if (m_AssetCache[scene] != null)
|
||||
if (m_Cache != null)
|
||||
{
|
||||
m_log.InfoFormat("[ASSET CONNECTOR]: Enabled asset caching for region {0}", scene.RegionInfo.RegionName);
|
||||
}
|
||||
|
@ -132,13 +135,31 @@ namespace OpenSim.Region.CoreModules.ServiceConnectors.Asset
|
|||
{
|
||||
string uri = m_ServerURI + "/assets/" + id;
|
||||
|
||||
AssetBase asset = SynchronousRestObjectPoster.
|
||||
BeginPostObject<int, AssetBase>("GET", uri, 0);
|
||||
AssetBase asset = null;
|
||||
if (m_Cache != null)
|
||||
asset = m_Cache.Get(id);
|
||||
|
||||
if (asset == null)
|
||||
{
|
||||
asset = SynchronousRestObjectPoster.
|
||||
BeginPostObject<int, AssetBase>("GET", uri, 0);
|
||||
|
||||
if (m_Cache != null)
|
||||
m_Cache.Cache(asset);
|
||||
}
|
||||
return asset;
|
||||
}
|
||||
|
||||
public AssetMetadata GetMetadata(string id)
|
||||
{
|
||||
if (m_Cache != null)
|
||||
{
|
||||
AssetBase fullAsset = m_Cache.Get(id);
|
||||
|
||||
if (fullAsset != null)
|
||||
return fullAsset.Metadata;
|
||||
}
|
||||
|
||||
string uri = m_ServerURI + "/assets/" + id + "/metadata";
|
||||
|
||||
AssetMetadata asset = SynchronousRestObjectPoster.
|
||||
|
@ -148,6 +169,14 @@ namespace OpenSim.Region.CoreModules.ServiceConnectors.Asset
|
|||
|
||||
public byte[] GetData(string id)
|
||||
{
|
||||
if (m_Cache != null)
|
||||
{
|
||||
AssetBase fullAsset = m_Cache.Get(id);
|
||||
|
||||
if (fullAsset != null)
|
||||
return fullAsset.Data;
|
||||
}
|
||||
|
||||
RestClient rc = new RestClient(m_ServerURI);
|
||||
rc.AddResourcePath("assets");
|
||||
rc.AddResourcePath(id);
|
||||
|
@ -171,33 +200,70 @@ namespace OpenSim.Region.CoreModules.ServiceConnectors.Asset
|
|||
return null;
|
||||
}
|
||||
|
||||
public bool Get(string id, Object sender, AssetRetrieved handler)
|
||||
{
|
||||
AssetBase asset = Get(id);
|
||||
handler(id, sender, asset);
|
||||
return true;
|
||||
}
|
||||
public string Store(AssetBase asset)
|
||||
{
|
||||
string uri = m_ServerURI + "/assets/";
|
||||
|
||||
string newID = SynchronousRestObjectPoster.
|
||||
BeginPostObject<AssetBase, string>("POST", uri, asset);
|
||||
|
||||
if (newID != String.Empty)
|
||||
{
|
||||
if (m_Cache != null)
|
||||
m_Cache.Cache(asset);
|
||||
}
|
||||
return newID;
|
||||
}
|
||||
|
||||
public bool UpdateContent(string id, byte[] data)
|
||||
{
|
||||
AssetBase asset = new AssetBase();
|
||||
asset.ID = id;
|
||||
AssetBase asset = null;
|
||||
|
||||
if (m_Cache != null)
|
||||
asset = m_Cache.Get(id);
|
||||
|
||||
if (asset == null)
|
||||
{
|
||||
AssetMetadata metadata = GetMetadata(id);
|
||||
if (metadata == null)
|
||||
return false;
|
||||
|
||||
asset = new AssetBase();
|
||||
asset.Metadata = metadata;
|
||||
}
|
||||
asset.Data = data;
|
||||
|
||||
string uri = m_ServerURI + "/assets/" + id;
|
||||
|
||||
return SynchronousRestObjectPoster.
|
||||
BeginPostObject<AssetBase, bool>("POST", uri, asset);
|
||||
if (SynchronousRestObjectPoster.
|
||||
BeginPostObject<AssetBase, bool>("POST", uri, asset))
|
||||
{
|
||||
if (m_Cache != null)
|
||||
m_Cache.Cache(asset);
|
||||
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
public bool Delete(string id)
|
||||
{
|
||||
string uri = m_ServerURI + "/assets/" + id;
|
||||
|
||||
return SynchronousRestObjectPoster.
|
||||
BeginPostObject<int, bool>("DELETE", uri, 0);
|
||||
if (SynchronousRestObjectPoster.
|
||||
BeginPostObject<int, bool>("DELETE", uri, 0))
|
||||
{
|
||||
if (m_Cache != null)
|
||||
m_Cache.Expire(id);
|
||||
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -94,6 +94,20 @@ namespace OpenSim.Services.AssetService
|
|||
return asset.Data;
|
||||
}
|
||||
|
||||
public bool Get(string id, Object sender, AssetRetrieved handler)
|
||||
{
|
||||
UUID assetID;
|
||||
|
||||
if (!UUID.TryParse(id, out assetID))
|
||||
return false;
|
||||
|
||||
AssetBase asset = m_Database.FetchAsset(assetID);
|
||||
|
||||
handler(id, sender, asset);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
public string Store(AssetBase asset)
|
||||
{
|
||||
m_Database.CreateAsset(asset);
|
||||
|
|
|
@ -25,10 +25,13 @@
|
|||
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
using System;
|
||||
using OpenSim.Framework;
|
||||
|
||||
namespace OpenSim.Services.Interfaces
|
||||
{
|
||||
public delegate void AssetRetrieved(string id, Object sender, AssetBase asset);
|
||||
|
||||
public interface IAssetService
|
||||
{
|
||||
// Three different ways to retrieve an asset
|
||||
|
@ -37,6 +40,8 @@ namespace OpenSim.Services.Interfaces
|
|||
AssetMetadata GetMetadata(string id);
|
||||
byte[] GetData(string id);
|
||||
|
||||
bool Get(string id, Object sender, AssetRetrieved handler);
|
||||
|
||||
// Creates a new asset
|
||||
// Returns a random ID if none is passed into it
|
||||
//
|
||||
|
|
Loading…
Reference in New Issue